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

Side by Side Diff: ui/message_center/views/message_list_view.cc

Issue 1187003002: Retires scoped_ptr for BoundsAnimator of message_list_view. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 5 years, 6 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
« no previous file with comments | « ui/message_center/views/message_list_view.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2015 The Chromium Authors. All rights reserved. 1 // Copyright (c) 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 "base/command_line.h" 5 #include "base/command_line.h"
6 #include "ui/gfx/animation/slide_animation.h" 6 #include "ui/gfx/animation/slide_animation.h"
7 #include "ui/message_center/message_center_style.h" 7 #include "ui/message_center/message_center_style.h"
8 #include "ui/message_center/message_center_switches.h" 8 #include "ui/message_center/message_center_switches.h"
9 #include "ui/message_center/views/message_center_view.h" 9 #include "ui/message_center/views/message_center_view.h"
10 #include "ui/message_center/views/message_list_view.h" 10 #include "ui/message_center/views/message_list_view.h"
11 #include "ui/message_center/views/message_view.h" 11 #include "ui/message_center/views/message_view.h"
12 #include "ui/views/animation/bounds_animator.h"
13 #include "ui/views/background.h" 12 #include "ui/views/background.h"
14 #include "ui/views/border.h" 13 #include "ui/views/border.h"
15 #include "ui/views/layout/box_layout.h" 14 #include "ui/views/layout/box_layout.h"
16 #include "ui/views/widget/widget.h" 15 #include "ui/views/widget/widget.h"
17 16
18 namespace message_center { 17 namespace message_center {
19 18
20 namespace { 19 namespace {
21 const int kAnimateClearingNextNotificationDelayMS = 40; 20 const int kAnimateClearingNextNotificationDelayMS = 40;
22 } // namespace 21 } // namespace
23 22
24 MessageListView::MessageListView(MessageCenterView* message_center_view, 23 MessageListView::MessageListView(MessageCenterView* message_center_view,
25 bool top_down) 24 bool top_down)
26 : message_center_view_(message_center_view), 25 : message_center_view_(message_center_view),
27 reposition_top_(-1), 26 reposition_top_(-1),
28 fixed_height_(0), 27 fixed_height_(0),
29 has_deferred_task_(false), 28 has_deferred_task_(false),
30 clear_all_started_(false), 29 clear_all_started_(false),
31 top_down_(top_down), 30 top_down_(top_down),
31 animator_(this),
32 weak_ptr_factory_(this) { 32 weak_ptr_factory_(this) {
33 views::BoxLayout* layout = 33 views::BoxLayout* layout =
34 new views::BoxLayout(views::BoxLayout::kVertical, 0, 0, 1); 34 new views::BoxLayout(views::BoxLayout::kVertical, 0, 0, 1);
35 layout->SetDefaultFlex(1); 35 layout->SetDefaultFlex(1);
36 SetLayoutManager(layout); 36 SetLayoutManager(layout);
37 37
38 // Set the margin to 0 for the layout. BoxLayout assumes the same margin 38 // Set the margin to 0 for the layout. BoxLayout assumes the same margin
39 // for top and bottom, but the bottom margin here should be smaller 39 // for top and bottom, but the bottom margin here should be smaller
40 // because of the shadow of message view. Use an empty border instead 40 // because of the shadow of message view. Use an empty border instead
41 // to provide this margin. 41 // to provide this margin.
42 gfx::Insets shadow_insets = MessageView::GetShadowInsets(); 42 gfx::Insets shadow_insets = MessageView::GetShadowInsets();
43 set_background( 43 set_background(
44 views::Background::CreateSolidBackground(kMessageCenterBackgroundColor)); 44 views::Background::CreateSolidBackground(kMessageCenterBackgroundColor));
45 SetBorder(views::Border::CreateEmptyBorder( 45 SetBorder(views::Border::CreateEmptyBorder(
46 top_down ? 0 : kMarginBetweenItems - shadow_insets.top(), /* top */ 46 top_down ? 0 : kMarginBetweenItems - shadow_insets.top(), /* top */
47 kMarginBetweenItems - shadow_insets.left(), /* left */ 47 kMarginBetweenItems - shadow_insets.left(), /* left */
48 top_down ? kMarginBetweenItems - shadow_insets.bottom() : 0, /* bottom */ 48 top_down ? kMarginBetweenItems - shadow_insets.bottom() : 0, /* bottom */
49 kMarginBetweenItems - shadow_insets.right() /* right */)); 49 kMarginBetweenItems - shadow_insets.right() /* right */));
50 animator_.AddObserver(this);
50 } 51 }
51 52
52 MessageListView::~MessageListView() { 53 MessageListView::~MessageListView() {
53 if (animator_.get()) 54 animator_.RemoveObserver(this);
54 animator_->RemoveObserver(this);
55 } 55 }
56 56
57 void MessageListView::Layout() { 57 void MessageListView::Layout() {
58 if (animator_.get() && animator_->IsAnimating()) 58 if (animator_.IsAnimating())
59 return; 59 return;
60 60
61 gfx::Rect child_area = GetContentsBounds(); 61 gfx::Rect child_area = GetContentsBounds();
62 int top = child_area.y(); 62 int top = child_area.y();
63 int between_items = 63 int between_items =
64 kMarginBetweenItems - MessageView::GetShadowInsets().bottom(); 64 kMarginBetweenItems - MessageView::GetShadowInsets().bottom();
65 65
66 for (int i = 0; i < child_count(); ++i) { 66 for (int i = 0; i < child_count(); ++i) {
67 views::View* child = child_at(i); 67 views::View* child = child_at(i);
68 if (!child->visible()) 68 if (!child->visible())
(...skipping 28 matching lines...) Expand all
97 } 97 }
98 98
99 void MessageListView::RemoveNotification(MessageView* view) { 99 void MessageListView::RemoveNotification(MessageView* view) {
100 DCHECK_EQ(view->parent(), this); 100 DCHECK_EQ(view->parent(), this);
101 if (GetContentsBounds().IsEmpty()) { 101 if (GetContentsBounds().IsEmpty()) {
102 delete view; 102 delete view;
103 } else { 103 } else {
104 if (view->layer()) { 104 if (view->layer()) {
105 deleting_views_.insert(view); 105 deleting_views_.insert(view);
106 } else { 106 } else {
107 if (animator_.get()) 107 animator_.StopAnimatingView(view);
108 animator_->StopAnimatingView(view);
109 delete view; 108 delete view;
110 } 109 }
111 DoUpdateIfPossible(); 110 DoUpdateIfPossible();
112 } 111 }
113 } 112 }
114 113
115 void MessageListView::UpdateNotification(MessageView* view, 114 void MessageListView::UpdateNotification(MessageView* view,
116 const Notification& notification) { 115 const Notification& notification) {
117 int index = GetIndexOf(view); 116 int index = GetIndexOf(view);
118 DCHECK_LE(0, index); // GetIndexOf is negative if not a child. 117 DCHECK_LE(0, index); // GetIndexOf is negative if not a child.
119 118
120 if (animator_.get()) 119 animator_.StopAnimatingView(view);
121 animator_->StopAnimatingView(view);
122 if (deleting_views_.find(view) != deleting_views_.end()) 120 if (deleting_views_.find(view) != deleting_views_.end())
123 deleting_views_.erase(view); 121 deleting_views_.erase(view);
124 if (deleted_when_done_.find(view) != deleted_when_done_.end()) 122 if (deleted_when_done_.find(view) != deleted_when_done_.end())
125 deleted_when_done_.erase(view); 123 deleted_when_done_.erase(view);
126 view->UpdateWithNotification(notification); 124 view->UpdateWithNotification(notification);
127 DoUpdateIfPossible(); 125 DoUpdateIfPossible();
128 } 126 }
129 127
130 gfx::Size MessageListView::GetPreferredSize() const { 128 gfx::Size MessageListView::GetPreferredSize() const {
131 int width = 0; 129 int width = 0;
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after
177 175
178 void MessageListView::SetRepositionTarget(const gfx::Rect& target) { 176 void MessageListView::SetRepositionTarget(const gfx::Rect& target) {
179 reposition_top_ = target.y(); 177 reposition_top_ = target.y();
180 fixed_height_ = GetHeightForWidth(width()); 178 fixed_height_ = GetHeightForWidth(width());
181 } 179 }
182 180
183 void MessageListView::ResetRepositionSession() { 181 void MessageListView::ResetRepositionSession() {
184 // Don't call DoUpdateIfPossible(), but let Layout() do the task without 182 // Don't call DoUpdateIfPossible(), but let Layout() do the task without
185 // animation. Reset will cause the change of the bubble size itself, and 183 // animation. Reset will cause the change of the bubble size itself, and
186 // animation from the old location will look weird. 184 // animation from the old location will look weird.
187 if (reposition_top_ >= 0 && animator_.get()) { 185 if (reposition_top_ >= 0) {
188 has_deferred_task_ = false; 186 has_deferred_task_ = false;
189 // cancel cause OnBoundsAnimatorDone which deletes |deleted_when_done_|. 187 // cancel cause OnBoundsAnimatorDone which deletes |deleted_when_done_|.
190 animator_->Cancel(); 188 animator_.Cancel();
191 STLDeleteContainerPointers(deleting_views_.begin(), deleting_views_.end()); 189 STLDeleteContainerPointers(deleting_views_.begin(), deleting_views_.end());
192 deleting_views_.clear(); 190 deleting_views_.clear();
193 adding_views_.clear(); 191 adding_views_.clear();
194 animator_.reset();
195 } 192 }
196 193
197 reposition_top_ = -1; 194 reposition_top_ = -1;
198 fixed_height_ = 0; 195 fixed_height_ = 0;
199 } 196 }
200 197
201 void MessageListView::ClearAllNotifications( 198 void MessageListView::ClearAllNotifications(
202 const gfx::Rect& visible_scroll_rect) { 199 const gfx::Rect& visible_scroll_rect) {
203 for (int i = 0; i < child_count(); ++i) { 200 for (int i = 0; i < child_count(); ++i) {
204 views::View* child = child_at(i); 201 views::View* child = child_at(i);
205 if (!child->visible()) 202 if (!child->visible())
206 continue; 203 continue;
207 if (gfx::IntersectRects(child->bounds(), visible_scroll_rect).IsEmpty()) 204 if (gfx::IntersectRects(child->bounds(), visible_scroll_rect).IsEmpty())
208 continue; 205 continue;
209 clearing_all_views_.push_back(child); 206 clearing_all_views_.push_back(child);
210 } 207 }
211 DoUpdateIfPossible(); 208 DoUpdateIfPossible();
212 } 209 }
213 210
214 void MessageListView::OnBoundsAnimatorProgressed( 211 void MessageListView::OnBoundsAnimatorProgressed(
215 views::BoundsAnimator* animator) { 212 views::BoundsAnimator* animator) {
216 DCHECK_EQ(animator_.get(), animator); 213 DCHECK_EQ(&animator_, animator);
217 for (std::set<views::View*>::iterator iter = deleted_when_done_.begin(); 214 for (std::set<views::View*>::iterator iter = deleted_when_done_.begin();
218 iter != deleted_when_done_.end(); ++iter) { 215 iter != deleted_when_done_.end(); ++iter) {
219 const gfx::SlideAnimation* animation = animator->GetAnimationForView(*iter); 216 const gfx::SlideAnimation* animation = animator->GetAnimationForView(*iter);
220 if (animation) 217 if (animation)
221 (*iter)->layer()->SetOpacity(animation->CurrentValueBetween(1.0, 0.0)); 218 (*iter)->layer()->SetOpacity(animation->CurrentValueBetween(1.0, 0.0));
222 } 219 }
223 } 220 }
224 221
225 void MessageListView::OnBoundsAnimatorDone(views::BoundsAnimator* animator) { 222 void MessageListView::OnBoundsAnimatorDone(views::BoundsAnimator* animator) {
226 STLDeleteContainerPointers(deleted_when_done_.begin(), 223 STLDeleteContainerPointers(deleted_when_done_.begin(),
(...skipping 20 matching lines...) Expand all
247 deleting_views_.end() && 244 deleting_views_.end() &&
248 deleted_when_done_.find(const_cast<views::View*>(child)) == 245 deleted_when_done_.find(const_cast<views::View*>(child)) ==
249 deleted_when_done_.end(); 246 deleted_when_done_.end();
250 } 247 }
251 248
252 void MessageListView::DoUpdateIfPossible() { 249 void MessageListView::DoUpdateIfPossible() {
253 gfx::Rect child_area = GetContentsBounds(); 250 gfx::Rect child_area = GetContentsBounds();
254 if (child_area.IsEmpty()) 251 if (child_area.IsEmpty())
255 return; 252 return;
256 253
257 if (animator_.get() && animator_->IsAnimating()) { 254 if (animator_.IsAnimating()) {
258 has_deferred_task_ = true; 255 has_deferred_task_ = true;
259 return; 256 return;
260 } 257 }
261 258
262 if (!animator_.get()) {
263 animator_.reset(new views::BoundsAnimator(this));
264 animator_->AddObserver(this);
265 }
266
267 if (!clearing_all_views_.empty()) { 259 if (!clearing_all_views_.empty()) {
268 AnimateClearingOneNotification(); 260 AnimateClearingOneNotification();
269 return; 261 return;
270 } 262 }
271 263
272 if (top_down_ || 264 if (top_down_ ||
273 base::CommandLine::ForCurrentProcess()->HasSwitch( 265 base::CommandLine::ForCurrentProcess()->HasSwitch(
274 switches::kEnableMessageCenterAlwaysScrollUpUponNotificationRemoval)) 266 switches::kEnableMessageCenterAlwaysScrollUpUponNotificationRemoval))
275 AnimateNotificationsBelowTarget(); 267 AnimateNotificationsBelowTarget();
276 else 268 else
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after
332 if (AnimateChild(child, bottom - child->height(), child->height())) 324 if (AnimateChild(child, bottom - child->height(), child->height()))
333 bottom -= child->height() + between_items; 325 bottom -= child->height() + between_items;
334 } 326 }
335 } 327 }
336 } 328 }
337 329
338 bool MessageListView::AnimateChild(views::View* child, int top, int height) { 330 bool MessageListView::AnimateChild(views::View* child, int top, int height) {
339 gfx::Rect child_area = GetContentsBounds(); 331 gfx::Rect child_area = GetContentsBounds();
340 if (adding_views_.find(child) != adding_views_.end()) { 332 if (adding_views_.find(child) != adding_views_.end()) {
341 child->SetBounds(child_area.right(), top, child_area.width(), height); 333 child->SetBounds(child_area.right(), top, child_area.width(), height);
342 animator_->AnimateViewTo( 334 animator_.AnimateViewTo(
343 child, gfx::Rect(child_area.x(), top, child_area.width(), height)); 335 child, gfx::Rect(child_area.x(), top, child_area.width(), height));
344 } else if (deleting_views_.find(child) != deleting_views_.end()) { 336 } else if (deleting_views_.find(child) != deleting_views_.end()) {
345 DCHECK(child->layer()); 337 DCHECK(child->layer());
346 // No moves, but animate to fade-out. 338 // No moves, but animate to fade-out.
347 animator_->AnimateViewTo(child, child->bounds()); 339 animator_.AnimateViewTo(child, child->bounds());
348 deleted_when_done_.insert(child); 340 deleted_when_done_.insert(child);
349 return false; 341 return false;
350 } else { 342 } else {
351 gfx::Rect target(child_area.x(), top, child_area.width(), height); 343 gfx::Rect target(child_area.x(), top, child_area.width(), height);
352 if (child->bounds().origin() != target.origin()) 344 if (child->bounds().origin() != target.origin())
353 animator_->AnimateViewTo(child, target); 345 animator_.AnimateViewTo(child, target);
354 else 346 else
355 child->SetBoundsRect(target); 347 child->SetBoundsRect(target);
356 } 348 }
357 return true; 349 return true;
358 } 350 }
359 351
360 void MessageListView::AnimateClearingOneNotification() { 352 void MessageListView::AnimateClearingOneNotification() {
361 DCHECK(!clearing_all_views_.empty()); 353 DCHECK(!clearing_all_views_.empty());
362 354
363 clear_all_started_ = true; 355 clear_all_started_ = true;
364 356
365 views::View* child = clearing_all_views_.front(); 357 views::View* child = clearing_all_views_.front();
366 clearing_all_views_.pop_front(); 358 clearing_all_views_.pop_front();
367 359
368 // Slide from left to right. 360 // Slide from left to right.
369 gfx::Rect new_bounds = child->bounds(); 361 gfx::Rect new_bounds = child->bounds();
370 new_bounds.set_x(new_bounds.right() + kMarginBetweenItems); 362 new_bounds.set_x(new_bounds.right() + kMarginBetweenItems);
371 animator_->AnimateViewTo(child, new_bounds); 363 animator_.AnimateViewTo(child, new_bounds);
372 364
373 // Schedule to start sliding out next notification after a short delay. 365 // Schedule to start sliding out next notification after a short delay.
374 if (!clearing_all_views_.empty()) { 366 if (!clearing_all_views_.empty()) {
375 base::MessageLoop::current()->PostDelayedTask( 367 base::MessageLoop::current()->PostDelayedTask(
376 FROM_HERE, base::Bind(&MessageListView::AnimateClearingOneNotification, 368 FROM_HERE, base::Bind(&MessageListView::AnimateClearingOneNotification,
377 weak_ptr_factory_.GetWeakPtr()), 369 weak_ptr_factory_.GetWeakPtr()),
378 base::TimeDelta::FromMilliseconds( 370 base::TimeDelta::FromMilliseconds(
379 kAnimateClearingNextNotificationDelayMS)); 371 kAnimateClearingNextNotificationDelayMS));
380 } 372 }
381 } 373 }
382 374
383 } // namespace message_center 375 } // namespace message_center
OLDNEW
« no previous file with comments | « ui/message_center/views/message_list_view.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698