Index: ui/message_center/views/notification_view_md.cc |
diff --git a/ui/message_center/views/notification_view_md.cc b/ui/message_center/views/notification_view_md.cc |
index 2f9e2c54fd3867cc1128fe72d7664471bc5c9b29..3ed99c231cf9bdc314e78ab8d66ee4a18f1098ba 100644 |
--- a/ui/message_center/views/notification_view_md.cc |
+++ b/ui/message_center/views/notification_view_md.cc |
@@ -49,9 +49,11 @@ namespace { |
constexpr gfx::Insets kContentRowPadding(4, 12, 12, 12); |
constexpr gfx::Insets kActionsRowPadding(8, 8, 8, 8); |
constexpr int kActionsRowHorizontalSpacing = 8; |
-constexpr gfx::Insets kImageContainerPadding(0, 12, 12, 12); |
constexpr gfx::Insets kActionButtonPadding(0, 12, 0, 12); |
constexpr gfx::Size kActionButtonMinSize(88, 32); |
+constexpr gfx::Insets kLargeImageContainerPadding(0, 12, 12, 12); |
+constexpr gfx::Size kLargeImageMinSize(328, 0); |
+constexpr gfx::Size kLargeImageMaxSize(328, 218); |
tetsui
2017/07/03 03:51:25
In new-style notification mock, the notification w
|
// Foreground of small icon image. |
constexpr SkColor kSmallImageBackgroundColor = SK_ColorWHITE; |
@@ -67,6 +69,8 @@ const float kActionButtonInkDropRippleVisibleOpacity = 0.08f; |
const float kActionButtonInkDropHighlightVisibleOpacity = 0.08f; |
// Text color of action button. |
const SkColor kActionButtonTextColor = SkColorSetRGB(0x33, 0x67, 0xD6); |
+// Background color of the large image. |
+const SkColor kLargeImageBackgroundColor = SkColorSetRGB(0xf5, 0xf5, 0xf5); |
// Max number of lines for message_view_. |
constexpr int kMaxLinesForMessageView = 1; |
@@ -312,6 +316,90 @@ NotificationButtonMD::CreateInkDropHighlight() const { |
return highlight; |
} |
+// LargeImageView ////////////////////////////////////////////////////////////// |
+ |
+class LargeImageView : public views::View { |
+ public: |
+ explicit LargeImageView(); |
+ ~LargeImageView() override; |
+ |
+ void SetImage(const gfx::ImageSkia& image); |
+ |
+ void OnPaint(gfx::Canvas* canvas) override; |
+ const char* GetClassName() const override; |
+ |
+ views::View* container() { return container_; } |
+ |
+ private: |
+ gfx::Size GetResizedImageSize(); |
+ |
+ views::View* container_ = nullptr; |
yoshiki
2017/07/28 06:13:03
nit: please add a comment about how the container
tetsui
2017/07/28 06:38:45
Done.
|
+ gfx::ImageSkia image_; |
+}; |
yoshiki
2017/07/28 06:13:03
Please add DISALLOW_COPY_AND_ASSIGN. This class sh
tetsui
2017/07/28 06:38:45
Done.
|
+ |
+LargeImageView::LargeImageView() { |
+ SetBackground(views::CreateSolidBackground(kLargeImageBackgroundColor)); |
+ container_ = new views::View; |
+ container_->SetLayoutManager(new views::FillLayout()); |
+ container_->SetBorder(views::CreateEmptyBorder(kLargeImageContainerPadding)); |
+ container_->SetBackground( |
+ views::CreateSolidBackground(message_center::kImageBackgroundColor)); |
+ container_->AddChildView(this); |
+} |
+ |
+LargeImageView::~LargeImageView() = default; |
+ |
+void LargeImageView::SetImage(const gfx::ImageSkia& image) { |
+ image_ = image; |
+ gfx::Size preferred_size = GetResizedImageSize(); |
+ preferred_size.SetToMax(kLargeImageMinSize); |
+ preferred_size.SetToMin(kLargeImageMaxSize); |
+ SetPreferredSize(preferred_size); |
+ SchedulePaint(); |
+ Layout(); |
+} |
+ |
+void LargeImageView::OnPaint(gfx::Canvas* canvas) { |
+ views::View::OnPaint(canvas); |
+ |
+ gfx::Size resized_size = GetResizedImageSize(); |
+ gfx::Size drawn_size = resized_size; |
+ drawn_size.SetToMin(kLargeImageMaxSize); |
+ gfx::Rect drawn_bounds = GetContentsBounds(); |
+ drawn_bounds.ClampToCenteredSize(drawn_size); |
+ |
+ gfx::ImageSkia resized_image = gfx::ImageSkiaOperations::CreateResizedImage( |
+ image_, skia::ImageOperations::RESIZE_BEST, resized_size); |
+ |
+ // Cut off the overflown part. |
+ gfx::ImageSkia drawn_image = gfx::ImageSkiaOperations::ExtractSubset( |
+ resized_image, gfx::Rect(drawn_size)); |
+ |
+ canvas->DrawImageInt(drawn_image, drawn_bounds.x(), drawn_bounds.y()); |
+} |
+ |
+const char* LargeImageView::GetClassName() const { |
+ return "LargeImageView"; |
+} |
+ |
+// Returns expected size of the image right after resizing. |
+// The GetResizedImageSize().width() <= kLargeImageMaxSize.width() holds, but |
+// GetResizedImageSize().height() may be larger than kLargeImageMaxSize.height() |
+// In this case, the overflown part will be just cutted off from the view. |
+gfx::Size LargeImageView::GetResizedImageSize() { |
+ gfx::Size original_size = image_.size(); |
+ if (original_size.width() <= kLargeImageMaxSize.width()) { |
+ return image_.size(); |
+ } else { |
yoshiki
2017/07/28 06:13:03
optional: I prefer the following style since this
tetsui
2017/07/28 06:38:45
Done.
|
+ const double proportion = |
+ original_size.height() / static_cast<double>(original_size.width()); |
+ gfx::Size resized_size; |
+ resized_size.SetSize(kLargeImageMaxSize.width(), |
+ kLargeImageMaxSize.width() * proportion); |
+ return resized_size; |
+ } |
+} |
+ |
} // anonymous namespace |
// //////////////////////////////////////////////////////////// |
@@ -649,7 +737,8 @@ void NotificationViewMD::CreateOrUpdateListItemViews( |
void NotificationViewMD::CreateOrUpdateIconView( |
const Notification& notification) { |
if (notification.type() == NOTIFICATION_TYPE_PROGRESS || |
- notification.type() == NOTIFICATION_TYPE_MULTIPLE) { |
+ notification.type() == NOTIFICATION_TYPE_MULTIPLE || |
+ notification.type() == NOTIFICATION_TYPE_IMAGE) { |
right_content_->RemoveChildView(icon_view_); |
icon_view_ = nullptr; |
return; |
@@ -676,43 +765,21 @@ void NotificationViewMD::CreateOrUpdateSmallIconView( |
void NotificationViewMD::CreateOrUpdateImageView( |
const Notification& notification) { |
- // |image_view_| is the view representing the area covered by the |
- // notification's image, including background and border. Its size can be |
- // specified in advance and images will be scaled to fit including a border if |
- // necessary. |
if (notification.image().IsEmpty()) { |
- if (image_container_) { |
- DCHECK(image_view_); |
- |
- left_content_->RemoveChildView(image_container_); |
- image_container_ = NULL; |
- image_view_ = NULL; |
- } else { |
- DCHECK(!image_view_); |
+ if (image_view_) { |
+ RemoveChildView(image_view_->container()); |
+ image_view_ = nullptr; |
} |
return; |
} |
- gfx::Size ideal_size(kNotificationPreferredImageWidth, |
- kNotificationPreferredImageHeight); |
- |
- if (!image_container_) { |
- image_container_ = new views::View(); |
- image_container_->SetLayoutManager(new views::FillLayout()); |
- image_container_->SetBorder( |
- views::CreateEmptyBorder(kImageContainerPadding)); |
- image_container_->SetBackground( |
- views::CreateSolidBackground(message_center::kImageBackgroundColor)); |
- |
- DCHECK(!image_view_); |
- image_view_ = new message_center::ProportionalImageView(ideal_size); |
- image_container_->AddChildView(image_view_); |
+ if (!image_view_) { |
+ image_view_ = new LargeImageView(); |
// Insert the created image container just after the |content_row_|. |
- AddChildViewAt(image_container_, GetIndexOf(content_row_) + 1); |
+ AddChildViewAt(image_view_->container(), GetIndexOf(content_row_) + 1); |
} |
- DCHECK(image_view_); |
- image_view_->SetImage(notification.image().AsImageSkia(), ideal_size); |
+ image_view_->SetImage(notification.image().AsImageSkia()); |
} |
void NotificationViewMD::CreateOrUpdateActionButtonViews( |
@@ -808,8 +875,8 @@ void NotificationViewMD::UpdateViewForExpandedState(bool expanded) { |
message_view_->SetLineLimit(expanded ? kMaxLinesForExpandedMessageView |
: kMaxLinesForMessageView); |
} |
- if (image_container_) |
- image_container_->SetVisible(expanded); |
+ if (image_view_) |
+ image_view_->container()->SetVisible(expanded); |
actions_row_->SetVisible(expanded && actions_row_->has_children()); |
for (size_t i = 1; i < item_views_.size(); ++i) { |
item_views_[i]->SetVisible(expanded); |