| OLD | NEW |
| 1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 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/rotator/screen_rotation_animator.h" | 5 #include "ash/rotator/screen_rotation_animator.h" |
| 6 | 6 |
| 7 #include "ash/ash_switches.h" | 7 #include "ash/ash_switches.h" |
| 8 #include "ash/display/window_tree_host_manager.h" | 8 #include "ash/display/window_tree_host_manager.h" |
| 9 #include "ash/public/cpp/shell_window_ids.h" | 9 #include "ash/public/cpp/shell_window_ids.h" |
| 10 #include "ash/rotator/screen_rotation_animation.h" | 10 #include "ash/rotator/screen_rotation_animation.h" |
| (...skipping 10 matching lines...) Expand all Loading... |
| 21 #include "ui/compositor/callback_layer_animation_observer.h" | 21 #include "ui/compositor/callback_layer_animation_observer.h" |
| 22 #include "ui/compositor/layer.h" | 22 #include "ui/compositor/layer.h" |
| 23 #include "ui/compositor/layer_animation_element.h" | 23 #include "ui/compositor/layer_animation_element.h" |
| 24 #include "ui/compositor/layer_animation_sequence.h" | 24 #include "ui/compositor/layer_animation_sequence.h" |
| 25 #include "ui/compositor/layer_animator.h" | 25 #include "ui/compositor/layer_animator.h" |
| 26 #include "ui/compositor/layer_owner.h" | 26 #include "ui/compositor/layer_owner.h" |
| 27 #include "ui/compositor/layer_tree_owner.h" | 27 #include "ui/compositor/layer_tree_owner.h" |
| 28 #include "ui/display/display.h" | 28 #include "ui/display/display.h" |
| 29 #include "ui/display/manager/display_manager.h" | 29 #include "ui/display/manager/display_manager.h" |
| 30 #include "ui/display/manager/managed_display_info.h" | 30 #include "ui/display/manager/managed_display_info.h" |
| 31 #include "ui/display/screen.h" |
| 31 #include "ui/gfx/animation/tween.h" | 32 #include "ui/gfx/animation/tween.h" |
| 32 #include "ui/gfx/geometry/point.h" | 33 #include "ui/gfx/geometry/point.h" |
| 33 #include "ui/gfx/geometry/rect.h" | 34 #include "ui/gfx/geometry/rect.h" |
| 34 #include "ui/gfx/geometry/rect_f.h" | 35 #include "ui/gfx/geometry/rect_f.h" |
| 35 #include "ui/gfx/transform.h" | 36 #include "ui/gfx/transform.h" |
| 36 #include "ui/gfx/transform_util.h" | 37 #include "ui/gfx/transform_util.h" |
| 37 #include "ui/wm/core/window_util.h" | 38 #include "ui/wm/core/window_util.h" |
| 38 | 39 |
| 39 namespace ash { | 40 namespace ash { |
| 40 | 41 |
| 41 namespace { | 42 namespace { |
| 42 | 43 |
| 43 // The number of degrees that the rotation animations animate through. | 44 // The number of degrees that the rotation animations animate through. |
| 44 const int kRotationDegrees = 20; | 45 const int kRotationDegrees = 20; |
| 45 | 46 |
| 46 // The time it takes for the rotation animations to run. | 47 // The time it takes for the rotation animations to run. |
| 47 const int kRotationDurationInMs = 250; | 48 const int kRotationDurationInMs = 250; |
| 48 | 49 |
| 49 // The rotation factors. | 50 // The rotation factors. |
| 50 const int kCounterClockWiseRotationFactor = 1; | 51 const int kCounterClockWiseRotationFactor = 1; |
| 51 const int kClockWiseRotationFactor = -1; | 52 const int kClockWiseRotationFactor = -1; |
| 52 | 53 |
| 53 display::Display::Rotation GetCurrentScreenRotation(int64_t display_id) { | 54 display::Display::Rotation GetCurrentScreenRotation(int64_t display_id) { |
| 54 return Shell::Get() | 55 return Shell::Get() |
| 55 ->display_manager() | 56 ->display_manager() |
| 56 ->GetDisplayInfo(display_id) | 57 ->GetDisplayInfo(display_id) |
| 57 .GetActiveRotation(); | 58 .GetActiveRotation(); |
| 58 } | 59 } |
| 59 | 60 |
| 60 bool IsDisplayIdValid(int64_t display_id) { | |
| 61 return Shell::Get()->display_manager()->IsDisplayIdValid(display_id); | |
| 62 } | |
| 63 | |
| 64 // 180 degree rotations should animate clock-wise. | 61 // 180 degree rotations should animate clock-wise. |
| 65 int GetRotationFactor(display::Display::Rotation initial_rotation, | 62 int GetRotationFactor(display::Display::Rotation initial_rotation, |
| 66 display::Display::Rotation new_rotation) { | 63 display::Display::Rotation new_rotation) { |
| 67 return (initial_rotation + 3) % 4 == new_rotation | 64 return (initial_rotation + 3) % 4 == new_rotation |
| 68 ? kCounterClockWiseRotationFactor | 65 ? kCounterClockWiseRotationFactor |
| 69 : kClockWiseRotationFactor; | 66 : kClockWiseRotationFactor; |
| 70 } | 67 } |
| 71 | 68 |
| 72 aura::Window* GetRootWindow(int64_t display_id) { | 69 aura::Window* GetRootWindow(int64_t display_id) { |
| 73 return Shell::Get()->window_tree_host_manager()->GetRootWindowForDisplayId( | 70 return Shell::Get()->window_tree_host_manager()->GetRootWindowForDisplayId( |
| (...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 127 return inverse; | 124 return inverse; |
| 128 } | 125 } |
| 129 | 126 |
| 130 // The |request_id| changed since last copy request, which means a | 127 // The |request_id| changed since last copy request, which means a |
| 131 // new rotation stated, we need to ignore this copy result. | 128 // new rotation stated, we need to ignore this copy result. |
| 132 bool IgnoreCopyResult(int64_t request_id, int64_t current_request_id) { | 129 bool IgnoreCopyResult(int64_t request_id, int64_t current_request_id) { |
| 133 DCHECK(request_id <= current_request_id); | 130 DCHECK(request_id <= current_request_id); |
| 134 return request_id < current_request_id; | 131 return request_id < current_request_id; |
| 135 } | 132 } |
| 136 | 133 |
| 137 // Creates a black mask layer and returns the |layer_owner|. | 134 bool RootWindowChangedForDisplayId(aura::Window* root_window, |
| 138 std::unique_ptr<ui::LayerOwner> CreateBlackMaskLayerOwner( | 135 int64_t display_id) { |
| 136 return root_window != GetRootWindow(display_id); |
| 137 } |
| 138 |
| 139 // Creates a mask layer and returns the |mask_layer_tree_owner|. |
| 140 std::unique_ptr<ui::LayerTreeOwner> CreateMaskLayerTreeOwner( |
| 139 const gfx::Rect& rect) { | 141 const gfx::Rect& rect) { |
| 140 std::unique_ptr<ui::Layer> black_mask_layer = | 142 std::unique_ptr<ui::Layer> mask_layer = |
| 141 base::MakeUnique<ui::Layer>(ui::LAYER_SOLID_COLOR); | 143 base::MakeUnique<ui::Layer>(ui::LAYER_SOLID_COLOR); |
| 142 black_mask_layer->SetBounds(rect); | 144 mask_layer->SetBounds(rect); |
| 143 black_mask_layer->SetColor(SK_ColorBLACK); | 145 mask_layer->SetColor(SK_ColorBLACK); |
| 144 std::unique_ptr<ui::LayerOwner> black_mask_layer_owner = | 146 return base::MakeUnique<ui::LayerTreeOwner>(std::move(mask_layer)); |
| 145 base::MakeUnique<ui::LayerOwner>(); | |
| 146 black_mask_layer_owner->SetLayer(std::move(black_mask_layer)); | |
| 147 return black_mask_layer_owner; | |
| 148 } | 147 } |
| 149 | 148 |
| 150 class ScreenRotationAnimationMetricsReporter | 149 class ScreenRotationAnimationMetricsReporter |
| 151 : public ui::AnimationMetricsReporter { | 150 : public ui::AnimationMetricsReporter { |
| 152 public: | 151 public: |
| 153 ScreenRotationAnimationMetricsReporter() = default; | 152 ScreenRotationAnimationMetricsReporter() = default; |
| 154 ~ScreenRotationAnimationMetricsReporter() override = default; | 153 ~ScreenRotationAnimationMetricsReporter() override = default; |
| 155 | 154 |
| 156 void Report(int value) override { | 155 void Report(int value) override { |
| 157 UMA_HISTOGRAM_PERCENTAGE("Ash.Rotation.AnimationSmoothness", value); | 156 UMA_HISTOGRAM_PERCENTAGE("Ash.Rotation.AnimationSmoothness", value); |
| 158 } | 157 } |
| 159 | 158 |
| 160 private: | 159 private: |
| 161 DISALLOW_COPY_AND_ASSIGN(ScreenRotationAnimationMetricsReporter); | 160 DISALLOW_COPY_AND_ASSIGN(ScreenRotationAnimationMetricsReporter); |
| 162 }; | 161 }; |
| 163 | 162 |
| 164 } // namespace | 163 } // namespace |
| 165 | 164 |
| 166 ScreenRotationAnimator::ScreenRotationAnimator(int64_t display_id) | 165 ScreenRotationAnimator::ScreenRotationAnimator(aura::Window* root_window) |
| 167 : display_id_(display_id), | 166 : root_window_(root_window), |
| 167 screen_rotation_container_layer_( |
| 168 GetScreenRotationContainer(root_window_)->layer()), |
| 168 screen_rotation_state_(IDLE), | 169 screen_rotation_state_(IDLE), |
| 169 rotation_request_id_(0), | 170 rotation_request_id_(0), |
| 170 metrics_reporter_( | 171 metrics_reporter_( |
| 171 base::MakeUnique<ScreenRotationAnimationMetricsReporter>()), | 172 base::MakeUnique<ScreenRotationAnimationMetricsReporter>()), |
| 172 disable_animation_timers_for_test_(false), | 173 disable_animation_timers_for_test_(false), |
| 173 has_switch_ash_disable_smooth_screen_rotation_( | 174 has_switch_ash_disable_smooth_screen_rotation_( |
| 174 base::CommandLine::ForCurrentProcess()->HasSwitch( | 175 base::CommandLine::ForCurrentProcess()->HasSwitch( |
| 175 switches::kAshDisableSmoothScreenRotation)), | 176 switches::kAshDisableSmoothScreenRotation)), |
| 176 root_window_(GetRootWindow(display_id_)), | |
| 177 screen_rotation_container_layer_( | |
| 178 GetScreenRotationContainer(root_window_)->layer()), | |
| 179 weak_factory_(this) {} | 177 weak_factory_(this) {} |
| 180 | 178 |
| 181 ScreenRotationAnimator::~ScreenRotationAnimator() { | 179 ScreenRotationAnimator::~ScreenRotationAnimator() { |
| 182 // To prevent a call to |AnimationEndedCallback()| from calling a method on | 180 // To prevent a call to |AnimationEndedCallback()| from calling a method on |
| 183 // the |animator_|. | 181 // the |animator_|. |
| 184 weak_factory_.InvalidateWeakPtrs(); | 182 weak_factory_.InvalidateWeakPtrs(); |
| 185 | 183 |
| 186 // Explicitly reset the |old_layer_tree_owner_| and |metrics_reporter_| in | 184 // Explicitly reset the |old_layer_tree_owner_| and |metrics_reporter_| in |
| 187 // order to make sure |metrics_reporter_| outlives the attached animation | 185 // order to make sure |metrics_reporter_| outlives the attached animation |
| 188 // sequence. | 186 // sequence. |
| 189 old_layer_tree_owner_.reset(); | 187 old_layer_tree_owner_.reset(); |
| 190 metrics_reporter_.reset(); | 188 metrics_reporter_.reset(); |
| 191 } | 189 } |
| 192 | 190 |
| 193 void ScreenRotationAnimator::StartRotationAnimation( | 191 void ScreenRotationAnimator::StartRotationAnimation( |
| 194 std::unique_ptr<ScreenRotationRequest> rotation_request) { | 192 std::unique_ptr<ScreenRotationRequest> rotation_request) { |
| 195 const display::Display::Rotation current_rotation = | 193 const display::Display::Rotation current_rotation = |
| 196 GetCurrentScreenRotation(display_id_); | 194 GetCurrentScreenRotation(rotation_request->display_id); |
| 197 if (current_rotation == rotation_request->new_rotation) { | 195 if (current_rotation == rotation_request->new_rotation) { |
| 198 // We need to call |ProcessAnimationQueue()| to prepare for next rotation | 196 // We need to call |ProcessAnimationQueue()| to prepare for next rotation |
| 199 // request. | 197 // request. |
| 200 ProcessAnimationQueue(); | 198 ProcessAnimationQueue(); |
| 201 return; | 199 return; |
| 202 } | 200 } |
| 203 | 201 |
| 204 rotation_request->old_rotation = current_rotation; | 202 rotation_request->old_rotation = current_rotation; |
| 205 if (has_switch_ash_disable_smooth_screen_rotation_) { | 203 if (has_switch_ash_disable_smooth_screen_rotation_) { |
| 206 StartSlowAnimation(std::move(rotation_request)); | 204 StartSlowAnimation(std::move(rotation_request)); |
| 207 } else { | 205 } else { |
| 208 std::unique_ptr<cc::CopyOutputRequest> copy_output_request = | 206 std::unique_ptr<cc::CopyOutputRequest> copy_output_request = |
| 209 cc::CopyOutputRequest::CreateRequest( | 207 cc::CopyOutputRequest::CreateRequest( |
| 210 CreateAfterCopyCallbackBeforeRotation(std::move(rotation_request))); | 208 CreateAfterCopyCallbackBeforeRotation(std::move(rotation_request))); |
| 211 RequestCopyScreenRotationContainerLayer(std::move(copy_output_request)); | 209 RequestCopyScreenRotationContainerLayer(std::move(copy_output_request)); |
| 212 screen_rotation_state_ = COPY_REQUESTED; | 210 screen_rotation_state_ = COPY_REQUESTED; |
| 213 } | 211 } |
| 214 } | 212 } |
| 215 | 213 |
| 216 void ScreenRotationAnimator::StartSlowAnimation( | 214 void ScreenRotationAnimator::StartSlowAnimation( |
| 217 std::unique_ptr<ScreenRotationRequest> rotation_request) { | 215 std::unique_ptr<ScreenRotationRequest> rotation_request) { |
| 218 CreateOldLayerTreeForSlowAnimation(); | 216 CreateOldLayerTreeForSlowAnimation(); |
| 219 SetRotation(rotation_request->old_rotation, rotation_request->new_rotation, | 217 SetRotation(rotation_request->display_id, rotation_request->old_rotation, |
| 220 rotation_request->source); | 218 rotation_request->new_rotation, rotation_request->source); |
| 221 AnimateRotation(std::move(rotation_request)); | 219 AnimateRotation(std::move(rotation_request)); |
| 222 } | 220 } |
| 223 | 221 |
| 224 void ScreenRotationAnimator::SetRotation( | 222 void ScreenRotationAnimator::SetRotation( |
| 223 int64_t display_id, |
| 225 display::Display::Rotation old_rotation, | 224 display::Display::Rotation old_rotation, |
| 226 display::Display::Rotation new_rotation, | 225 display::Display::Rotation new_rotation, |
| 227 display::Display::RotationSource source) { | 226 display::Display::RotationSource source) { |
| 228 // Allow compositor locks to extend timeout, so that screen rotation only | 227 // Allow compositor locks to extend timeout, so that screen rotation only |
| 229 // takes output copy after contents are properlly resized, such as wallpaper | 228 // takes output copy after contents are properlly resized, such as wallpaper |
| 230 // and ARC apps. | 229 // and ARC apps. |
| 231 ui::Compositor* compositor = root_window_->layer()->GetCompositor(); | 230 ui::Compositor* compositor = root_window_->layer()->GetCompositor(); |
| 232 compositor->set_allow_locks_to_extend_timeout(true); | 231 compositor->set_allow_locks_to_extend_timeout(true); |
| 233 Shell::Get()->display_manager()->SetDisplayRotation(display_id_, new_rotation, | 232 Shell::Get()->display_manager()->SetDisplayRotation(display_id, new_rotation, |
| 234 source); | 233 source); |
| 235 compositor->set_allow_locks_to_extend_timeout(false); | 234 compositor->set_allow_locks_to_extend_timeout(false); |
| 236 const display::Display display = | 235 const display::Display display = |
| 237 Shell::Get()->display_manager()->GetDisplayForId(display_id_); | 236 Shell::Get()->display_manager()->GetDisplayForId(display_id); |
| 238 old_layer_tree_owner_->root()->SetTransform( | 237 old_layer_tree_owner_->root()->SetTransform( |
| 239 CreateScreenRotationOldLayerTransformForDisplay(old_rotation, | 238 CreateScreenRotationOldLayerTransformForDisplay(old_rotation, |
| 240 new_rotation, display)); | 239 new_rotation, display)); |
| 241 } | 240 } |
| 242 | 241 |
| 243 void ScreenRotationAnimator::RequestCopyScreenRotationContainerLayer( | 242 void ScreenRotationAnimator::RequestCopyScreenRotationContainerLayer( |
| 244 std::unique_ptr<cc::CopyOutputRequest> copy_output_request) { | 243 std::unique_ptr<cc::CopyOutputRequest> copy_output_request) { |
| 245 copy_output_request->set_area( | 244 copy_output_request->set_area( |
| 246 gfx::Rect(screen_rotation_container_layer_->size())); | 245 gfx::Rect(screen_rotation_container_layer_->size())); |
| 247 screen_rotation_container_layer_->RequestCopyOfOutput( | 246 screen_rotation_container_layer_->RequestCopyOfOutput( |
| (...skipping 16 matching lines...) Expand all Loading... |
| 264 OnScreenRotationContainerLayerCopiedAfterRotation, | 263 OnScreenRotationContainerLayerCopiedAfterRotation, |
| 265 weak_factory_.GetWeakPtr(), | 264 weak_factory_.GetWeakPtr(), |
| 266 base::Passed(&rotation_request)); | 265 base::Passed(&rotation_request)); |
| 267 } | 266 } |
| 268 | 267 |
| 269 void ScreenRotationAnimator::OnScreenRotationContainerLayerCopiedBeforeRotation( | 268 void ScreenRotationAnimator::OnScreenRotationContainerLayerCopiedBeforeRotation( |
| 270 std::unique_ptr<ScreenRotationRequest> rotation_request, | 269 std::unique_ptr<ScreenRotationRequest> rotation_request, |
| 271 std::unique_ptr<cc::CopyOutputResult> result) { | 270 std::unique_ptr<cc::CopyOutputResult> result) { |
| 272 if (IgnoreCopyResult(rotation_request->id, rotation_request_id_)) | 271 if (IgnoreCopyResult(rotation_request->id, rotation_request_id_)) |
| 273 return; | 272 return; |
| 274 // Abort rotation and animation if the display was removed. | 273 // Abort rotation and animation if the display was removed or the |
| 275 if (!IsDisplayIdValid(display_id_)) { | 274 // |root_window| was changed for |display_id|. |
| 275 if (RootWindowChangedForDisplayId(root_window_, |
| 276 rotation_request->display_id)) { |
| 276 ProcessAnimationQueue(); | 277 ProcessAnimationQueue(); |
| 277 return; | 278 return; |
| 278 } | 279 } |
| 279 // Abort animation and set the rotation to target rotation when the copy | 280 // Abort animation and set the rotation to target rotation when the copy |
| 280 // request has been canceled or failed. It would fail if, for examples: a) The | 281 // request has been canceled or failed. It would fail if, for examples: a) The |
| 281 // layer is removed from the compositor and destroye before committing the | 282 // layer is removed from the compositor and destroye before committing the |
| 282 // request to the compositor. b) The compositor is shutdown. | 283 // request to the compositor. b) The compositor is shutdown. |
| 283 if (result->IsEmpty()) { | 284 if (result->IsEmpty()) { |
| 284 Shell::Get()->display_manager()->SetDisplayRotation( | 285 Shell::Get()->display_manager()->SetDisplayRotation( |
| 285 display_id_, rotation_request->new_rotation, rotation_request->source); | 286 rotation_request->display_id, rotation_request->new_rotation, |
| 287 rotation_request->source); |
| 286 ProcessAnimationQueue(); | 288 ProcessAnimationQueue(); |
| 287 return; | 289 return; |
| 288 } | 290 } |
| 289 | 291 |
| 290 old_layer_tree_owner_ = CopyLayerTree(std::move(result)); | 292 old_layer_tree_owner_ = CopyLayerTree(std::move(result)); |
| 291 AddLayerAtTopOfWindowLayers(root_window_, old_layer_tree_owner_->root()); | 293 AddLayerAtTopOfWindowLayers(root_window_, old_layer_tree_owner_->root()); |
| 292 SetRotation(rotation_request->old_rotation, rotation_request->new_rotation, | 294 SetRotation(rotation_request->display_id, rotation_request->old_rotation, |
| 293 rotation_request->source); | 295 rotation_request->new_rotation, rotation_request->source); |
| 294 std::unique_ptr<cc::CopyOutputRequest> copy_output_request = | 296 std::unique_ptr<cc::CopyOutputRequest> copy_output_request = |
| 295 cc::CopyOutputRequest::CreateRequest( | 297 cc::CopyOutputRequest::CreateRequest( |
| 296 CreateAfterCopyCallbackAfterRotation(std::move(rotation_request))); | 298 CreateAfterCopyCallbackAfterRotation(std::move(rotation_request))); |
| 297 RequestCopyScreenRotationContainerLayer(std::move(copy_output_request)); | 299 RequestCopyScreenRotationContainerLayer(std::move(copy_output_request)); |
| 298 } | 300 } |
| 299 | 301 |
| 300 void ScreenRotationAnimator::OnScreenRotationContainerLayerCopiedAfterRotation( | 302 void ScreenRotationAnimator::OnScreenRotationContainerLayerCopiedAfterRotation( |
| 301 std::unique_ptr<ScreenRotationRequest> rotation_request, | 303 std::unique_ptr<ScreenRotationRequest> rotation_request, |
| 302 std::unique_ptr<cc::CopyOutputResult> result) { | 304 std::unique_ptr<cc::CopyOutputResult> result) { |
| 303 if (IgnoreCopyResult(rotation_request->id, rotation_request_id_)) | 305 if (IgnoreCopyResult(rotation_request->id, rotation_request_id_)) |
| 304 return; | 306 return; |
| 305 // In the following cases, abort animation: | 307 // In the following cases, abort animation: |
| 306 // 1) if the display was removed, | 308 // 1) if the display was removed, |
| 307 // 2) the copy request has been canceled or failed. It would fail if, | 309 // 2) if the |root_window| was changed for |display_id|, |
| 310 // 3) the copy request has been canceled or failed. It would fail if, |
| 308 // for examples: a) The layer is removed from the compositor and destroye | 311 // for examples: a) The layer is removed from the compositor and destroye |
| 309 // before committing the request to the compositor. b) The compositor is | 312 // before committing the request to the compositor. b) The compositor is |
| 310 // shutdown. | 313 // shutdown. |
| 311 if (!IsDisplayIdValid(display_id_) || result->IsEmpty()) { | 314 if (RootWindowChangedForDisplayId(root_window_, |
| 315 rotation_request->display_id) || |
| 316 result->IsEmpty()) { |
| 312 ProcessAnimationQueue(); | 317 ProcessAnimationQueue(); |
| 313 return; | 318 return; |
| 314 } | 319 } |
| 315 | 320 |
| 316 new_layer_tree_owner_ = CopyLayerTree(std::move(result)); | 321 new_layer_tree_owner_ = CopyLayerTree(std::move(result)); |
| 317 AddLayerBelowWindowLayer(root_window_, old_layer_tree_owner_->root(), | 322 AddLayerBelowWindowLayer(root_window_, old_layer_tree_owner_->root(), |
| 318 new_layer_tree_owner_->root()); | 323 new_layer_tree_owner_->root()); |
| 319 AnimateRotation(std::move(rotation_request)); | 324 AnimateRotation(std::move(rotation_request)); |
| 320 } | 325 } |
| 321 | 326 |
| (...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 356 const gfx::Point pivot = gfx::Point(rotated_screen_bounds.width() / 2, | 361 const gfx::Point pivot = gfx::Point(rotated_screen_bounds.width() / 2, |
| 357 rotated_screen_bounds.height() / 2); | 362 rotated_screen_bounds.height() / 2); |
| 358 | 363 |
| 359 ui::Layer* new_root_layer; | 364 ui::Layer* new_root_layer; |
| 360 if (!new_layer_tree_owner_ || | 365 if (!new_layer_tree_owner_ || |
| 361 has_switch_ash_disable_smooth_screen_rotation_) { | 366 has_switch_ash_disable_smooth_screen_rotation_) { |
| 362 new_root_layer = screen_rotation_container_layer_; | 367 new_root_layer = screen_rotation_container_layer_; |
| 363 } else { | 368 } else { |
| 364 new_root_layer = new_layer_tree_owner_->root(); | 369 new_root_layer = new_layer_tree_owner_->root(); |
| 365 // Add a black mask layer on top of |screen_rotation_container_layer_|. | 370 // Add a black mask layer on top of |screen_rotation_container_layer_|. |
| 366 black_mask_layer_owner_ = CreateBlackMaskLayerOwner( | 371 mask_layer_tree_owner_ = CreateMaskLayerTreeOwner( |
| 367 gfx::Rect(screen_rotation_container_layer_->size())); | 372 gfx::Rect(screen_rotation_container_layer_->size())); |
| 368 AddLayerBelowWindowLayer(root_window_, new_root_layer, | 373 AddLayerBelowWindowLayer(root_window_, new_root_layer, |
| 369 black_mask_layer_owner_->layer()); | 374 mask_layer_tree_owner_->root()); |
| 370 } | 375 } |
| 371 | 376 |
| 372 std::unique_ptr<ScreenRotationAnimation> new_layer_screen_rotation = | 377 std::unique_ptr<ScreenRotationAnimation> new_layer_screen_rotation = |
| 373 base::MakeUnique<ScreenRotationAnimation>( | 378 base::MakeUnique<ScreenRotationAnimation>( |
| 374 new_root_layer, kRotationDegrees * rotation_factor, | 379 new_root_layer, kRotationDegrees * rotation_factor, |
| 375 0 /* end_degrees */, new_root_layer->opacity(), | 380 0 /* end_degrees */, new_root_layer->opacity(), |
| 376 new_root_layer->opacity() /* target_opacity */, pivot, duration, | 381 new_root_layer->opacity() /* target_opacity */, pivot, duration, |
| 377 tween_type); | 382 tween_type); |
| 378 | 383 |
| 379 ui::LayerAnimator* new_layer_animator = new_root_layer->GetAnimator(); | 384 ui::LayerAnimator* new_layer_animator = new_root_layer->GetAnimator(); |
| (...skipping 54 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 434 } | 439 } |
| 435 | 440 |
| 436 void ScreenRotationAnimator::Rotate(display::Display::Rotation new_rotation, | 441 void ScreenRotationAnimator::Rotate(display::Display::Rotation new_rotation, |
| 437 display::Display::RotationSource source) { | 442 display::Display::RotationSource source) { |
| 438 // |rotation_request_id_| is used to skip stale requests. Before the layer | 443 // |rotation_request_id_| is used to skip stale requests. Before the layer |
| 439 // CopyOutputResult callback called, there could have new rotation request. | 444 // CopyOutputResult callback called, there could have new rotation request. |
| 440 // Increases |rotation_request_id_| for each new request and in the callback, | 445 // Increases |rotation_request_id_| for each new request and in the callback, |
| 441 // we compare the |rotation_request.id| and |rotation_request_id_| to | 446 // we compare the |rotation_request.id| and |rotation_request_id_| to |
| 442 // determine the stale status. | 447 // determine the stale status. |
| 443 rotation_request_id_++; | 448 rotation_request_id_++; |
| 449 const int64_t display_id = |
| 450 display::Screen::GetScreen()->GetDisplayNearestWindow(root_window_).id(); |
| 444 std::unique_ptr<ScreenRotationRequest> rotation_request = | 451 std::unique_ptr<ScreenRotationRequest> rotation_request = |
| 445 base::MakeUnique<ScreenRotationRequest>(rotation_request_id_, | 452 base::MakeUnique<ScreenRotationRequest>(rotation_request_id_, display_id, |
| 446 new_rotation, source); | 453 new_rotation, source); |
| 447 switch (screen_rotation_state_) { | 454 switch (screen_rotation_state_) { |
| 448 case IDLE: | 455 case IDLE: |
| 449 case COPY_REQUESTED: | 456 case COPY_REQUESTED: |
| 450 StartRotationAnimation(std::move(rotation_request)); | 457 StartRotationAnimation(std::move(rotation_request)); |
| 451 break; | 458 break; |
| 452 case ROTATING: | 459 case ROTATING: |
| 453 last_pending_request_ = std::move(rotation_request); | 460 last_pending_request_ = std::move(rotation_request); |
| 454 // The pending request will be processed when the | 461 // The pending request will be processed when the |
| 455 // |AnimationEndedCallback()| should be called after |StopAnimating()|. | 462 // |AnimationEndedCallback()| should be called after |StopAnimating()|. |
| 456 StopAnimating(); | 463 StopAnimating(); |
| 457 break; | 464 break; |
| 458 } | 465 } |
| 459 } | 466 } |
| 460 | 467 |
| 461 void ScreenRotationAnimator::AddScreenRotationAnimatorObserver( | 468 void ScreenRotationAnimator::AddScreenRotationAnimatorObserver( |
| 462 ScreenRotationAnimatorObserver* observer) { | 469 ScreenRotationAnimatorObserver* observer) { |
| 463 screen_rotation_animator_observers_.AddObserver(observer); | 470 screen_rotation_animator_observers_.AddObserver(observer); |
| 464 } | 471 } |
| 465 | 472 |
| 466 void ScreenRotationAnimator::RemoveScreenRotationAnimatorObserver( | 473 void ScreenRotationAnimator::RemoveScreenRotationAnimatorObserver( |
| 467 ScreenRotationAnimatorObserver* observer) { | 474 ScreenRotationAnimatorObserver* observer) { |
| 468 screen_rotation_animator_observers_.RemoveObserver(observer); | 475 screen_rotation_animator_observers_.RemoveObserver(observer); |
| 469 } | 476 } |
| 470 | 477 |
| 471 void ScreenRotationAnimator::ProcessAnimationQueue() { | 478 void ScreenRotationAnimator::ProcessAnimationQueue() { |
| 472 screen_rotation_state_ = IDLE; | 479 screen_rotation_state_ = IDLE; |
| 473 if (IsDisplayIdValid(display_id_) && black_mask_layer_owner_) | |
| 474 root_window_->layer()->Remove(black_mask_layer_owner_->layer()); | |
| 475 old_layer_tree_owner_.reset(); | 480 old_layer_tree_owner_.reset(); |
| 476 new_layer_tree_owner_.reset(); | 481 new_layer_tree_owner_.reset(); |
| 477 black_mask_layer_owner_.reset(); | 482 mask_layer_tree_owner_.reset(); |
| 478 if (last_pending_request_ && IsDisplayIdValid(display_id_)) { | 483 if (last_pending_request_ && |
| 484 !RootWindowChangedForDisplayId(root_window_, |
| 485 last_pending_request_->display_id)) { |
| 479 StartRotationAnimation(std::move(last_pending_request_)); | 486 StartRotationAnimation(std::move(last_pending_request_)); |
| 480 return; | 487 return; |
| 481 } | 488 } |
| 482 | 489 |
| 483 // This is only used in test to notify animator observer. | 490 // This is only used in test to notify animator observer. |
| 484 for (auto& observer : screen_rotation_animator_observers_) | 491 for (auto& observer : screen_rotation_animator_observers_) |
| 485 observer.OnScreenRotationAnimationFinished(this); | 492 observer.OnScreenRotationAnimationFinished(this); |
| 486 } | 493 } |
| 487 | 494 |
| 488 void ScreenRotationAnimator::StopAnimating() { | 495 void ScreenRotationAnimator::StopAnimating() { |
| 489 // |old_layer_tree_owner_| new_layer_tree_owner_| could be nullptr if another | 496 // |old_layer_tree_owner_| new_layer_tree_owner_| could be nullptr if another |
| 490 // the rotation request comes before the copy request finished. | 497 // the rotation request comes before the copy request finished. |
| 491 if (old_layer_tree_owner_) | 498 if (old_layer_tree_owner_) |
| 492 old_layer_tree_owner_->root()->GetAnimator()->StopAnimating(); | 499 old_layer_tree_owner_->root()->GetAnimator()->StopAnimating(); |
| 493 if (new_layer_tree_owner_) | 500 if (new_layer_tree_owner_) |
| 494 new_layer_tree_owner_->root()->GetAnimator()->StopAnimating(); | 501 new_layer_tree_owner_->root()->GetAnimator()->StopAnimating(); |
| 495 if (IsDisplayIdValid(display_id_) && black_mask_layer_owner_) | 502 mask_layer_tree_owner_.reset(); |
| 496 root_window_->layer()->Remove(black_mask_layer_owner_->layer()); | |
| 497 } | 503 } |
| 498 | 504 |
| 499 } // namespace ash | 505 } // namespace ash |
| OLD | NEW |