Chromium Code Reviews| 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 "ui/message_center/views/notification_view.h" | 5 #include "ui/message_center/views/notification_view.h" |
| 6 | 6 |
| 7 #include <stddef.h> | 7 #include <stddef.h> |
| 8 | 8 |
| 9 #include "base/command_line.h" | 9 #include "base/command_line.h" |
| 10 #include "base/macros.h" | 10 #include "base/macros.h" |
| (...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 52 | 52 |
| 53 #if defined(OS_WIN) | 53 #if defined(OS_WIN) |
| 54 #include "ui/base/win/shell.h" | 54 #include "ui/base/win/shell.h" |
| 55 #endif | 55 #endif |
| 56 | 56 |
| 57 namespace { | 57 namespace { |
| 58 | 58 |
| 59 // Dimensions. | 59 // Dimensions. |
| 60 const int kProgressBarBottomPadding = 0; | 60 const int kProgressBarBottomPadding = 0; |
| 61 | 61 |
| 62 const int kCloseIconTopPadding = 5; | |
| 63 const int kCloseIconRightPadding = 5; | |
| 64 | |
| 62 // static | 65 // static |
| 63 scoped_ptr<views::Border> MakeEmptyBorder(int top, | 66 scoped_ptr<views::Border> MakeEmptyBorder(int top, |
| 64 int left, | 67 int left, |
| 65 int bottom, | 68 int bottom, |
| 66 int right) { | 69 int right) { |
| 67 return views::Border::CreateEmptyBorder(top, left, bottom, right); | 70 return views::Border::CreateEmptyBorder(top, left, bottom, right); |
| 68 } | 71 } |
| 69 | 72 |
| 70 // static | 73 // static |
| 71 scoped_ptr<views::Border> MakeTextBorder(int padding, int top, int bottom) { | 74 scoped_ptr<views::Border> MakeTextBorder(int padding, int top, int bottom) { |
| (...skipping 149 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 221 // targeting. Using the center point of |rect| preserves this function's | 224 // targeting. Using the center point of |rect| preserves this function's |
| 222 // expected behavior for the time being. | 225 // expected behavior for the time being. |
| 223 gfx::Point point = rect.CenterPoint(); | 226 gfx::Point point = rect.CenterPoint(); |
| 224 | 227 |
| 225 // Want to return this for underlying views, otherwise GetCursor is not | 228 // Want to return this for underlying views, otherwise GetCursor is not |
| 226 // called. But buttons are exceptions, they'll have their own event handlings. | 229 // called. But buttons are exceptions, they'll have their own event handlings. |
| 227 std::vector<views::View*> buttons(action_buttons_.begin(), | 230 std::vector<views::View*> buttons(action_buttons_.begin(), |
| 228 action_buttons_.end()); | 231 action_buttons_.end()); |
| 229 if (settings_button_view_) | 232 if (settings_button_view_) |
| 230 buttons.push_back(settings_button_view_); | 233 buttons.push_back(settings_button_view_); |
| 231 buttons.push_back(close_button()); | 234 if (close_button_) |
| 235 buttons.push_back(close_button_.get()); | |
| 232 | 236 |
| 233 for (size_t i = 0; i < buttons.size(); ++i) { | 237 for (size_t i = 0; i < buttons.size(); ++i) { |
| 234 gfx::Point point_in_child = point; | 238 gfx::Point point_in_child = point; |
| 235 ConvertPointToTarget(this, buttons[i], &point_in_child); | 239 ConvertPointToTarget(this, buttons[i], &point_in_child); |
| 236 if (buttons[i]->HitTestPoint(point_in_child)) | 240 if (buttons[i]->HitTestPoint(point_in_child)) |
| 237 return buttons[i]->GetEventHandlerForPoint(point_in_child); | 241 return buttons[i]->GetEventHandlerForPoint(point_in_child); |
| 238 } | 242 } |
| 239 | 243 |
| 240 return root; | 244 return root; |
| 241 } | 245 } |
| 242 | 246 |
| 243 void NotificationView::CreateOrUpdateViews(const Notification& notification) { | 247 void NotificationView::CreateOrUpdateViews(const Notification& notification) { |
| 248 CreateOrUpdateCloseButtonView(notification); | |
| 244 CreateOrUpdateTitleView(notification); | 249 CreateOrUpdateTitleView(notification); |
| 245 CreateOrUpdateMessageView(notification); | 250 CreateOrUpdateMessageView(notification); |
| 246 CreateOrUpdateProgressBarView(notification); | 251 CreateOrUpdateProgressBarView(notification); |
| 247 CreateOrUpdateListItemViews(notification); | 252 CreateOrUpdateListItemViews(notification); |
| 248 CreateOrUpdateIconView(notification); | 253 CreateOrUpdateIconView(notification); |
| 249 CreateOrUpdateImageView(notification); | 254 CreateOrUpdateImageView(notification); |
| 250 CreateOrUpdateContextMessageView(notification); | 255 CreateOrUpdateContextMessageView(notification); |
| 251 CreateOrUpdateSettingsButtonView(notification); | 256 CreateOrUpdateSettingsButtonView(notification); |
| 252 CreateOrUpdateActionButtonViews(notification); | 257 CreateOrUpdateActionButtonViews(notification); |
| 253 } | 258 } |
| (...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 301 new views::BoxLayout(views::BoxLayout::kVertical, 0, 0, 0)); | 306 new views::BoxLayout(views::BoxLayout::kVertical, 0, 0, 0)); |
| 302 AddChildView(bottom_view_); | 307 AddChildView(bottom_view_); |
| 303 | 308 |
| 304 CreateOrUpdateViews(notification); | 309 CreateOrUpdateViews(notification); |
| 305 | 310 |
| 306 // Put together the different content and control views. Layering those allows | 311 // Put together the different content and control views. Layering those allows |
| 307 // for proper layout logic and it also allows the close button and small | 312 // for proper layout logic and it also allows the close button and small |
| 308 // image to overlap the content as needed to provide large enough click and | 313 // image to overlap the content as needed to provide large enough click and |
| 309 // touch areas (<http://crbug.com/168822> and <http://crbug.com/168856>). | 314 // touch areas (<http://crbug.com/168822> and <http://crbug.com/168856>). |
| 310 AddChildView(small_image()); | 315 AddChildView(small_image()); |
| 311 AddChildView(close_button()); | |
| 312 SetAccessibleName(notification); | 316 SetAccessibleName(notification); |
| 313 | 317 |
| 314 SetEventTargeter( | 318 SetEventTargeter( |
| 315 scoped_ptr<views::ViewTargeter>(new views::ViewTargeter(this))); | 319 scoped_ptr<views::ViewTargeter>(new views::ViewTargeter(this))); |
| 316 } | 320 } |
| 317 | 321 |
| 318 NotificationView::~NotificationView() { | 322 NotificationView::~NotificationView() { |
| 319 } | 323 } |
| 320 | 324 |
| 321 gfx::Size NotificationView::GetPreferredSize() const { | 325 gfx::Size NotificationView::GetPreferredSize() const { |
| (...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 371 title_lines = | 375 title_lines = |
| 372 title_view_->GetLinesForWidthAndLimit(width(), kMaxTitleLines); | 376 title_view_->GetLinesForWidthAndLimit(width(), kMaxTitleLines); |
| 373 } | 377 } |
| 374 if (message_view_) | 378 if (message_view_) |
| 375 message_view_->SetLineLimit(GetMessageLineLimit(title_lines, width())); | 379 message_view_->SetLineLimit(GetMessageLineLimit(title_lines, width())); |
| 376 | 380 |
| 377 // Top views. | 381 // Top views. |
| 378 int top_height = top_view_->GetHeightForWidth(content_width); | 382 int top_height = top_view_->GetHeightForWidth(content_width); |
| 379 top_view_->SetBounds(insets.left(), insets.top(), content_width, top_height); | 383 top_view_->SetBounds(insets.left(), insets.top(), content_width, top_height); |
| 380 | 384 |
| 385 // Close button. | |
| 386 if (close_button_) { | |
| 387 gfx::Rect content_bounds = GetContentsBounds(); | |
| 388 gfx::Size close_size(close_button_->GetPreferredSize()); | |
| 389 gfx::Rect close_rect(content_bounds.right() - close_size.width(), | |
| 390 content_bounds.y(), close_size.width(), | |
| 391 close_size.height()); | |
| 392 close_button_->SetBoundsRect(close_rect); | |
| 393 } | |
| 394 | |
| 381 // Icon. | 395 // Icon. |
| 382 icon_view_->SetBounds(insets.left(), insets.top(), kIconSize, kIconSize); | 396 icon_view_->SetBounds(insets.left(), insets.top(), kIconSize, kIconSize); |
| 383 | 397 |
| 384 // Settings & Bottom views. | 398 // Settings & Bottom views. |
| 385 int bottom_y = insets.top() + std::max(top_height, kIconSize); | 399 int bottom_y = insets.top() + std::max(top_height, kIconSize); |
| 386 int bottom_height = bottom_view_->GetHeightForWidth(content_width); | 400 int bottom_height = bottom_view_->GetHeightForWidth(content_width); |
| 387 | 401 |
| 388 if (settings_button_view_) { | 402 if (settings_button_view_) { |
| 389 gfx::Size settings_size(settings_button_view_->GetPreferredSize()); | 403 gfx::Size settings_size(settings_button_view_->GetPreferredSize()); |
| 390 settings_button_view_->SetBounds(content_width - settings_size.width(), | 404 settings_button_view_->SetBounds(content_width - settings_size.width(), |
| (...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 438 } | 452 } |
| 439 | 453 |
| 440 // See if the button pressed was an action button. | 454 // See if the button pressed was an action button. |
| 441 for (size_t i = 0; i < action_buttons_.size(); ++i) { | 455 for (size_t i = 0; i < action_buttons_.size(); ++i) { |
| 442 if (sender == action_buttons_[i]) { | 456 if (sender == action_buttons_[i]) { |
| 443 controller_->ClickOnNotificationButton(id, i); | 457 controller_->ClickOnNotificationButton(id, i); |
| 444 return; | 458 return; |
| 445 } | 459 } |
| 446 } | 460 } |
| 447 | 461 |
| 462 if (close_button_ && sender == close_button_.get()) { | |
| 463 controller_->RemoveNotification(notification_id(), true); // By user. | |
|
dewittj
2016/02/10 00:03:15
nit: should be consistent in comments, so this sho
| |
| 464 } | |
| 465 | |
| 448 // Let the superclass handle everything else. | 466 // Let the superclass handle everything else. |
| 449 // Warning: This may cause the NotificationView itself to be deleted, | 467 // Warning: This may cause the NotificationView itself to be deleted, |
| 450 // so don't do anything afterwards. | 468 // so don't do anything afterwards. |
| 451 MessageView::ButtonPressed(sender, event); | 469 MessageView::ButtonPressed(sender, event); |
| 452 } | 470 } |
| 453 | 471 |
| 454 void NotificationView::ClickOnNotification(const std::string& notification_id) { | 472 void NotificationView::ClickOnNotification(const std::string& notification_id) { |
| 455 controller_->ClickOnNotification(notification_id); | 473 controller_->ClickOnNotification(notification_id); |
| 456 } | 474 } |
| 457 | 475 |
| (...skipping 307 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 765 if (new_buttons) { | 783 if (new_buttons) { |
| 766 Layout(); | 784 Layout(); |
| 767 views::Widget* widget = GetWidget(); | 785 views::Widget* widget = GetWidget(); |
| 768 if (widget != NULL) { | 786 if (widget != NULL) { |
| 769 widget->SetSize(widget->GetContentsView()->GetPreferredSize()); | 787 widget->SetSize(widget->GetContentsView()->GetPreferredSize()); |
| 770 GetWidget()->SynthesizeMouseMoveEvent(); | 788 GetWidget()->SynthesizeMouseMoveEvent(); |
| 771 } | 789 } |
| 772 } | 790 } |
| 773 } | 791 } |
| 774 | 792 |
| 793 void NotificationView::CreateOrUpdateCloseButtonView( | |
| 794 const Notification& notification) { | |
| 795 set_slide_out_enabled(!notification.pinned()); | |
| 796 | |
| 797 if (!notification.pinned() && !close_button_) { | |
| 798 PaddedButton* close = new PaddedButton(this); | |
| 799 close->SetPadding(-kCloseIconRightPadding, kCloseIconTopPadding); | |
| 800 close->SetNormalImage(IDR_NOTIFICATION_CLOSE); | |
| 801 close->SetHoveredImage(IDR_NOTIFICATION_CLOSE_HOVER); | |
| 802 close->SetPressedImage(IDR_NOTIFICATION_CLOSE_PRESSED); | |
| 803 close->set_animate_on_state_change(false); | |
| 804 close->SetAccessibleName(l10n_util::GetStringUTF16( | |
| 805 IDS_MESSAGE_CENTER_CLOSE_NOTIFICATION_BUTTON_ACCESSIBLE_NAME)); | |
| 806 // The close button should be added to view hierarchy by the derived class. | |
| 807 // This ensures that it is on top of other views. | |
| 808 close->set_owned_by_client(); | |
| 809 close_button_.reset(close); | |
| 810 AddChildView(close_button_.get()); | |
| 811 } else if (notification.pinned() && close_button_) { | |
| 812 close_button_.reset(); | |
| 813 } | |
| 814 } | |
| 815 | |
| 775 int NotificationView::GetMessageLineLimit(int title_lines, int width) const { | 816 int NotificationView::GetMessageLineLimit(int title_lines, int width) const { |
| 776 // Image notifications require that the image must be kept flush against | 817 // Image notifications require that the image must be kept flush against |
| 777 // their icons, but we can allow more text if no image. | 818 // their icons, but we can allow more text if no image. |
| 778 int effective_title_lines = std::max(0, title_lines - 1); | 819 int effective_title_lines = std::max(0, title_lines - 1); |
| 779 int line_reduction_from_title = (image_view_ ? 1 : 2) * effective_title_lines; | 820 int line_reduction_from_title = (image_view_ ? 1 : 2) * effective_title_lines; |
| 780 if (!image_view_) { | 821 if (!image_view_) { |
| 781 // Title lines are counted as twice as big as message lines for the purpose | 822 // Title lines are counted as twice as big as message lines for the purpose |
| 782 // of this calculation. | 823 // of this calculation. |
| 783 // The effect from the title reduction here should be: | 824 // The effect from the title reduction here should be: |
| 784 // * 0 title lines: 5 max lines message. | 825 // * 0 title lines: 5 max lines message. |
| (...skipping 21 matching lines...) Expand all Loading... | |
| 806 std::max(0, message_line_limit - line_reduction_from_title); | 847 std::max(0, message_line_limit - line_reduction_from_title); |
| 807 | 848 |
| 808 return message_line_limit; | 849 return message_line_limit; |
| 809 } | 850 } |
| 810 | 851 |
| 811 int NotificationView::GetMessageHeight(int width, int limit) const { | 852 int NotificationView::GetMessageHeight(int width, int limit) const { |
| 812 return message_view_ ? | 853 return message_view_ ? |
| 813 message_view_->GetSizeForWidthAndLines(width, limit).height() : 0; | 854 message_view_->GetSizeForWidthAndLines(width, limit).height() : 0; |
| 814 } | 855 } |
| 815 | 856 |
| 857 bool NotificationView::IsCloseButtonFocused() { | |
| 858 if (!close_button_) | |
| 859 return false; | |
| 860 | |
| 861 views::FocusManager* focus_manager = GetFocusManager(); | |
| 862 return focus_manager && | |
| 863 focus_manager->GetFocusedView() == close_button_.get(); | |
| 864 } | |
| 865 | |
| 866 void NotificationView::RequestFocusOnCloseButton() { | |
| 867 if (close_button_) | |
| 868 close_button_->RequestFocus(); | |
| 869 } | |
| 870 | |
| 871 bool NotificationView::IsPinned() { | |
| 872 return !close_button_; | |
| 873 } | |
| 874 | |
| 816 } // namespace message_center | 875 } // namespace message_center |
| OLD | NEW |