Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(660)

Side by Side Diff: athena/wm/split_view_controller.cc

Issue 513313003: Fix crash when using title drag on a window opened while split view is active (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 6 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2014 The Chromium Authors. All rights reserved. 1 // Copyright 2014 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 "athena/wm/split_view_controller.h" 5 #include "athena/wm/split_view_controller.h"
6 6
7 #include <cmath> 7 #include <cmath>
8 8
9 #include "athena/wm/public/window_list_provider.h" 9 #include "athena/wm/public/window_list_provider.h"
10 #include "athena/wm/public/window_manager.h" 10 #include "athena/wm/public/window_manager.h"
(...skipping 94 matching lines...) Expand 10 before | Expand all | Expand 10 after
105 CHECK(IsSplitViewModeActive()); 105 CHECK(IsSplitViewModeActive());
106 CHECK(replace_with); 106 CHECK(replace_with);
107 CHECK(window == left_window_ || window == right_window_); 107 CHECK(window == left_window_ || window == right_window_);
108 CHECK(replace_with != left_window_ && replace_with != right_window_); 108 CHECK(replace_with != left_window_ && replace_with != right_window_);
109 #if !defined(NDEBUG) 109 #if !defined(NDEBUG)
110 aura::Window::Windows windows = window_list_provider_->GetWindowList(); 110 aura::Window::Windows windows = window_list_provider_->GetWindowList();
111 DCHECK(std::find(windows.begin(), windows.end(), replace_with) != 111 DCHECK(std::find(windows.begin(), windows.end(), replace_with) !=
112 windows.end()); 112 windows.end());
113 #endif 113 #endif
114 114
115 replace_with->SetBounds(window->bounds());
116 replace_with->SetTransform(gfx::Transform());
117 if (window == left_window_) 115 if (window == left_window_)
118 left_window_ = replace_with; 116 left_window_ = replace_with;
119 else 117 else
120 right_window_ = replace_with; 118 right_window_ = replace_with;
121 wm::ActivateWindow(replace_with); 119 wm::ActivateWindow(replace_with);
120 UpdateLayout(false);
122 window->SetTransform(gfx::Transform()); 121 window->SetTransform(gfx::Transform());
122 window->Hide();
123 } 123 }
124 124
125 void SplitViewController::DeactivateSplitMode() { 125 void SplitViewController::DeactivateSplitMode() {
126 CHECK_NE(SCROLLING, state_); 126 CHECK_NE(SCROLLING, state_);
127 state_ = INACTIVE; 127 state_ = INACTIVE;
128 UpdateLayout(false);
128 left_window_ = right_window_ = NULL; 129 left_window_ = right_window_ = NULL;
129 } 130 }
130 131
131 gfx::Rect SplitViewController::GetLeftTargetBounds() { 132 gfx::Rect SplitViewController::GetLeftTargetBounds() {
132 gfx::Rect work_area = 133 gfx::Rect work_area =
133 gfx::Screen::GetNativeScreen()->GetPrimaryDisplay().work_area(); 134 gfx::Screen::GetNativeScreen()->GetPrimaryDisplay().work_area();
134 return gfx::Rect(0, 0, container_->bounds().width() / 2, work_area.height()); 135 return gfx::Rect(0, 0, container_->bounds().width() / 2, work_area.height());
135 } 136 }
136 137
137 gfx::Rect SplitViewController::GetRightTargetBounds() { 138 gfx::Rect SplitViewController::GetRightTargetBounds() {
138 gfx::Rect work_area = 139 gfx::Rect work_area =
139 gfx::Screen::GetNativeScreen()->GetPrimaryDisplay().work_area(); 140 gfx::Screen::GetNativeScreen()->GetPrimaryDisplay().work_area();
140 int container_width = container_->bounds().width(); 141 int container_width = container_->bounds().width();
141 return gfx::Rect( 142 return gfx::Rect(
142 container_width / 2, 0, container_width / 2, work_area.height()); 143 container_width / 2, 0, container_width / 2, work_area.height());
143 } 144 }
144 145
145 void SplitViewController::UpdateLayout(bool animate) { 146 void SplitViewController::UpdateLayout(bool animate) {
146 if (!left_window_) 147 if (!left_window_)
147 return; 148 return;
oshima 2014/08/29 21:57:06 can this happen?
148 CHECK(right_window_); 149 CHECK(right_window_);
149 gfx::Transform left_transform; 150
150 gfx::Transform right_transform; 151 if (state_ == INACTIVE && !animate) {
151 int container_width = container_->GetBoundsInScreen().width(); 152 if (!wm::IsActiveWindow(left_window_))
152 if (state_ == ACTIVE) { 153 left_window_->Hide();
153 // Windows should be resized via an animation when entering the ACTIVE 154 if (!wm::IsActiveWindow(right_window_))
154 // state. 155 right_window_->Hide();
155 CHECK(animate); 156 SetWindowTransforms(gfx::Transform(), gfx::Transform(), false);
156 // We scale the windows here, but when the animation finishes, we reset 157 return;
157 // the scaling and update the window bounds to the proper size - see
158 // OnAnimationCompleted().
159 left_transform = GetTargetTransformForBoundsAnimation(
160 left_window_->bounds(), GetLeftTargetBounds());
161 right_transform = GetTargetTransformForBoundsAnimation(
162 right_window_->bounds(), GetRightTargetBounds());
163 } else {
164 left_transform.Translate(separator_position_ - container_width, 0);
165 right_transform.Translate(separator_position_, 0);
166 } 158 }
159
167 left_window_->Show(); 160 left_window_->Show();
168 right_window_->Show(); 161 right_window_->Show();
169 SetWindowTransform(left_window_, left_transform, animate); 162 if (state_ == ACTIVE) {
170 SetWindowTransform(right_window_, right_transform, animate); 163 if (animate) {
164 gfx::Transform left_transform = GetTargetTransformForBoundsAnimation(
165 left_window_->bounds(), GetLeftTargetBounds());
166 gfx::Transform right_transform = GetTargetTransformForBoundsAnimation(
167 right_window_->bounds(), GetRightTargetBounds());
168 SetWindowTransforms(left_transform, right_transform, true);
169 } else {
170 left_window_->SetBounds(GetLeftTargetBounds());
171 right_window_->SetBounds(GetRightTargetBounds());
172 SetWindowTransforms(gfx::Transform(), gfx::Transform(), false);
173 }
174 } else {
175 gfx::Transform left_transform;
176 left_transform.Translate(separator_position_ - container_->bounds().width(),
177 0);
178 gfx::Transform right_transform;
179 right_transform.Translate(separator_position_, 0);
180 SetWindowTransforms(left_transform, right_transform, animate);
181 }
182 // Note: |left_window_| and |right_window_| may be NULL if calling
183 // SetWindowTransforms():
184 // - caused the in-progress animation to abort.
185 // - started a zero duration animation.
171 } 186 }
172 187
173 void SplitViewController::SetWindowTransform(aura::Window* window, 188 void SplitViewController::SetWindowTransforms(
174 const gfx::Transform& transform, 189 const gfx::Transform& left_transform,
175 bool animate) { 190 const gfx::Transform& right_transform,
191 bool animate) {
176 if (animate) { 192 if (animate) {
177 scoped_refptr<ui::LayerAnimator> animator = window->layer()->GetAnimator(); 193 ui::ScopedLayerAnimationSettings left_settings(
178 ui::ScopedLayerAnimationSettings settings(animator); 194 left_window_->layer()->GetAnimator());
179 settings.SetPreemptionStrategy( 195 left_settings.SetPreemptionStrategy(
180 ui::LayerAnimator::IMMEDIATELY_ANIMATE_TO_NEW_TARGET); 196 ui::LayerAnimator::IMMEDIATELY_ANIMATE_TO_NEW_TARGET);
181 settings.AddObserver(new ui::ClosureAnimationObserver( 197 left_window_->SetTransform(left_transform);
198
199 ui::ScopedLayerAnimationSettings right_settings(
200 right_window_->layer()->GetAnimator());
201 right_settings.SetPreemptionStrategy(
202 ui::LayerAnimator::IMMEDIATELY_ANIMATE_TO_NEW_TARGET);
203 right_settings.AddObserver(new ui::ClosureAnimationObserver(
182 base::Bind(&SplitViewController::OnAnimationCompleted, 204 base::Bind(&SplitViewController::OnAnimationCompleted,
183 weak_factory_.GetWeakPtr(), 205 weak_factory_.GetWeakPtr())));
184 window))); 206 right_window_->SetTransform(right_transform);
185 window->SetTransform(transform);
186 } else { 207 } else {
187 window->SetTransform(transform); 208 left_window_->SetTransform(left_transform);
209 right_window_->SetTransform(right_transform);
188 } 210 }
189 } 211 }
190 212
191 void SplitViewController::OnAnimationCompleted(aura::Window* window) { 213 void SplitViewController::OnAnimationCompleted() {
192 // Animation can be cancelled when deactivated. 214 // Animation can be cancelled when deactivated.
193 if (left_window_ == NULL) 215 if (left_window_ == NULL)
194 return; 216 return;
195 DCHECK(window == left_window_ || window == right_window_); 217 UpdateLayout(false);
196 if (state_ == ACTIVE) { 218
197 window->SetTransform(gfx::Transform()); 219 if (state_ == INACTIVE) {
198 if (window == left_window_) 220 left_window_ = NULL;
199 left_window_->SetBounds(GetLeftTargetBounds()); 221 right_window_ = NULL;
200 else
201 right_window_->SetBounds(GetRightTargetBounds());
202 } else {
203 int container_width = container_->bounds().width();
204 window->SetTransform(gfx::Transform());
205 if (window == left_window_) {
206 if (separator_position_ == 0)
207 left_window_->Hide();
208 if (state_ == INACTIVE)
209 left_window_ = NULL;
210 } else {
211 if (separator_position_ == container_width)
212 right_window_->Hide();
213 if (state_ == INACTIVE)
214 right_window_ = NULL;
215 }
216 } 222 }
217 } 223 }
218 224
219 void SplitViewController::UpdateSeparatorPositionFromScrollDelta(float delta) { 225 void SplitViewController::UpdateSeparatorPositionFromScrollDelta(float delta) {
220 gfx::Screen* screen = gfx::Screen::GetScreenFor(container_); 226 gfx::Screen* screen = gfx::Screen::GetScreenFor(container_);
221 const gfx::Rect& display_bounds = 227 const gfx::Rect& display_bounds =
222 screen->GetDisplayNearestWindow(container_).bounds(); 228 screen->GetDisplayNearestWindow(container_).bounds();
223 gfx::Rect container_bounds = container_->GetBoundsInScreen(); 229 gfx::Rect container_bounds = container_->GetBoundsInScreen();
224 separator_position_ = 230 separator_position_ =
225 delta > 0 ? ((int)delta) + display_bounds.x() - container_bounds.x() 231 delta > 0 ? ((int)delta) + display_bounds.x() - container_bounds.x()
(...skipping 62 matching lines...) Expand 10 before | Expand all | Expand 10 after
288 } 294 }
289 295
290 bool SplitViewController::CanScroll() { 296 bool SplitViewController::CanScroll() {
291 // TODO(mfomitchev): return false in vertical orientation, in full screen. 297 // TODO(mfomitchev): return false in vertical orientation, in full screen.
292 bool result = (!IsSplitViewModeActive() && 298 bool result = (!IsSplitViewModeActive() &&
293 window_list_provider_->GetWindowList().size() >= 2); 299 window_list_provider_->GetWindowList().size() >= 2);
294 return result; 300 return result;
295 } 301 }
296 302
297 } // namespace athena 303 } // namespace athena
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698