1 // Copyright 2019 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "components/media_message_center/media_notification_background_impl.h"
6
7 #include <memory>
8
9 #include "base/i18n/base_i18n_switches.h"
10 #include "base/test/icu_test_util.h"
11 #include "base/test/scoped_command_line.h"
12 #include "testing/gtest/include/gtest/gtest.h"
13 #include "ui/gfx/color_analysis.h"
14 #include "ui/gfx/color_utils.h"
15 #include "ui/gfx/skia_util.h"
16 #include "ui/native_theme/test_native_theme.h"
17 #include "ui/views/test/test_views.h"
18
19 namespace media_message_center {
20
21 namespace {
22
23 constexpr double kLightLuma = 0.9;
24 constexpr double kNormalLuma = 0.5;
25 constexpr double kDarkLuma = 0.2;
26
27 constexpr double kMutedSaturation = 0.2;
28 constexpr double kVibrantSaturation = 0.8;
29
30 constexpr int kDefaultForegroundArtworkHeight = 100;
31
32 constexpr SkColor kDarkBackgroundColor = SK_ColorBLACK;
33
34 class TestDarkTheme : public ui::TestNativeTheme {
35 public:
36 TestDarkTheme() = default;
37 ~TestDarkTheme() override = default;
38
39 // ui::NativeTheme implementation.
GetSystemColor(ColorId color_id,ColorScheme color_scheme) const40 SkColor GetSystemColor(ColorId color_id,
41 ColorScheme color_scheme) const override {
42 if (color_id == kColorId_BubbleBackground)
43 return kDarkBackgroundColor;
44 return ui::TestNativeTheme::GetSystemColor(color_id, color_scheme);
45 }
46 };
47
GetColorFromSL(double s,double l)48 SkColor GetColorFromSL(double s, double l) {
49 return color_utils::HSLToSkColor({0.2, s, l}, SK_AlphaOPAQUE);
50 }
51
CreateTestBackgroundImage(SkColor first_color,SkColor second_color,int second_height)52 gfx::ImageSkia CreateTestBackgroundImage(SkColor first_color,
53 SkColor second_color,
54 int second_height) {
55 constexpr SkColor kRightHandSideColor = SK_ColorMAGENTA;
56
57 DCHECK_NE(kRightHandSideColor, first_color);
58 DCHECK_NE(kRightHandSideColor, second_color);
59
60 SkBitmap bitmap;
61 bitmap.allocN32Pixels(100, 100);
62
63 int first_height = bitmap.height() - second_height;
64 int right_width = bitmap.width() / 2;
65
66 // Fill the right hand side of the image with a constant color. The color
67 // derivation algorithm does not look at the right hand side so we should
68 // never see |kRightHandSideColor|.
69 bitmap.erase(kRightHandSideColor,
70 {right_width, 0, bitmap.width(), bitmap.height()});
71
72 // Fill the left hand side with |first_color|.
73 bitmap.erase(first_color, {0, 0, right_width, first_height});
74
75 // Fill the left hand side with |second_color|.
76 bitmap.erase(second_color, {0, first_height, right_width, bitmap.height()});
77
78 return gfx::ImageSkia::CreateFrom1xBitmap(bitmap);
79 }
80
CreateTestBackgroundImage(SkColor color)81 gfx::ImageSkia CreateTestBackgroundImage(SkColor color) {
82 return CreateTestBackgroundImage(color, SK_ColorTRANSPARENT, 0);
83 }
84
85 } // namespace
86
87 class MediaNotificationBackgroundImplTest : public testing::Test {
88 public:
89 MediaNotificationBackgroundImplTest() = default;
90 ~MediaNotificationBackgroundImplTest() override = default;
91
SetUp()92 void SetUp() override {
93 background_ =
94 std::make_unique<MediaNotificationBackgroundImpl>(10, 10, 0.1);
95
96 EXPECT_FALSE(GetBackgroundColor().has_value());
97 }
98
TearDown()99 void TearDown() override { background_.reset(); }
100
background() const101 MediaNotificationBackgroundImpl* background() const {
102 return background_.get();
103 }
104
GetBackgroundColor() const105 base::Optional<SkColor> GetBackgroundColor() const {
106 return background_->background_color_;
107 }
108
GetForegroundColor() const109 base::Optional<SkColor> GetForegroundColor() const {
110 return background_->foreground_color_;
111 }
112
GetBackgroundFaviconColorShadeFactor() const113 double GetBackgroundFaviconColorShadeFactor() const {
114 return MediaNotificationBackgroundImpl::kBackgroundFaviconColorShadeFactor;
115 }
116
117 private:
118 std::unique_ptr<MediaNotificationBackgroundImpl> background_;
119
120 DISALLOW_COPY_AND_ASSIGN(MediaNotificationBackgroundImplTest);
121 };
122
123 // If we have no artwork then we should use the default background color.
TEST_F(MediaNotificationBackgroundImplTest,DeriveBackgroundColor_NoArtwork)124 TEST_F(MediaNotificationBackgroundImplTest, DeriveBackgroundColor_NoArtwork) {
125 background()->UpdateArtwork(gfx::ImageSkia());
126 EXPECT_FALSE(GetBackgroundColor().has_value());
127 }
128
129 // If we have artwork with no popular color then we should use the default
130 // background color.
TEST_F(MediaNotificationBackgroundImplTest,DeriveBackgroundColor_NoPopularColor)131 TEST_F(MediaNotificationBackgroundImplTest,
132 DeriveBackgroundColor_NoPopularColor) {
133 background()->UpdateArtwork(CreateTestBackgroundImage(SK_ColorTRANSPARENT));
134 EXPECT_FALSE(GetBackgroundColor().has_value());
135 }
136
137 // If the most popular color is not white or black then we should use that
138 // color.
TEST_F(MediaNotificationBackgroundImplTest,DeriveBackgroundColor_PopularNonWhiteBlackColor)139 TEST_F(MediaNotificationBackgroundImplTest,
140 DeriveBackgroundColor_PopularNonWhiteBlackColor) {
141 constexpr SkColor kTestColor = SK_ColorYELLOW;
142 background()->UpdateArtwork(CreateTestBackgroundImage(kTestColor));
143 EXPECT_EQ(kTestColor, GetBackgroundColor());
144 }
145
TEST_F(MediaNotificationBackgroundImplTest,DeriveBackgroundColor_NoArtworkAfterHavingOne)146 TEST_F(MediaNotificationBackgroundImplTest,
147 DeriveBackgroundColor_NoArtworkAfterHavingOne) {
148 constexpr SkColor kTestColor = SK_ColorYELLOW;
149 background()->UpdateArtwork(CreateTestBackgroundImage(kTestColor));
150 EXPECT_EQ(kTestColor, GetBackgroundColor());
151
152 background()->UpdateArtwork(gfx::ImageSkia());
153 EXPECT_FALSE(GetBackgroundColor().has_value());
154 }
155
156 // Favicons should be used when available but have a shade applying to them.
TEST_F(MediaNotificationBackgroundImplTest,DeriveBackgroundColor_PopularNonWhiteBlackColorFavicon)157 TEST_F(MediaNotificationBackgroundImplTest,
158 DeriveBackgroundColor_PopularNonWhiteBlackColorFavicon) {
159 constexpr SkColor kTestColor = SK_ColorYELLOW;
160 background()->UpdateFavicon(CreateTestBackgroundImage(kTestColor));
161 const SkColor expected_color = SkColorSetRGB(
162 SkColorGetR(kTestColor) * GetBackgroundFaviconColorShadeFactor(),
163 SkColorGetG(kTestColor) * GetBackgroundFaviconColorShadeFactor(),
164 SkColorGetB(kTestColor) * GetBackgroundFaviconColorShadeFactor());
165 EXPECT_EQ(expected_color, GetBackgroundColor());
166 }
167
TEST_F(MediaNotificationBackgroundImplTest,DeriveBackgroundColor_NoFaviconAfterHavingOne)168 TEST_F(MediaNotificationBackgroundImplTest,
169 DeriveBackgroundColor_NoFaviconAfterHavingOne) {
170 constexpr SkColor kTestColor = SK_ColorYELLOW;
171 background()->UpdateFavicon(CreateTestBackgroundImage(kTestColor));
172 const SkColor expected_color = SkColorSetRGB(
173 SkColorGetR(kTestColor) * GetBackgroundFaviconColorShadeFactor(),
174 SkColorGetG(kTestColor) * GetBackgroundFaviconColorShadeFactor(),
175 SkColorGetB(kTestColor) * GetBackgroundFaviconColorShadeFactor());
176 EXPECT_EQ(expected_color, GetBackgroundColor());
177
178 background()->UpdateFavicon(gfx::ImageSkia());
179 EXPECT_FALSE(GetBackgroundColor().has_value());
180 }
181
TEST_F(MediaNotificationBackgroundImplTest,DeriveBackgroundColor_FaviconSetThenArtwork)182 TEST_F(MediaNotificationBackgroundImplTest,
183 DeriveBackgroundColor_FaviconSetThenArtwork) {
184 constexpr SkColor kArtworkColor = SK_ColorYELLOW;
185 constexpr SkColor kFaviconColor = SK_ColorRED;
186
187 background()->UpdateFavicon(CreateTestBackgroundImage(kFaviconColor));
188 background()->UpdateArtwork(CreateTestBackgroundImage(kArtworkColor));
189
190 EXPECT_EQ(kArtworkColor, GetBackgroundColor());
191 }
192
TEST_F(MediaNotificationBackgroundImplTest,DeriveBackgroundColor_ArtworkSetThenFavicon)193 TEST_F(MediaNotificationBackgroundImplTest,
194 DeriveBackgroundColor_ArtworkSetThenFavicon) {
195 constexpr SkColor kArtworkColor = SK_ColorYELLOW;
196 constexpr SkColor kFaviconColor = SK_ColorRED;
197
198 background()->UpdateArtwork(CreateTestBackgroundImage(kArtworkColor));
199 background()->UpdateFavicon(CreateTestBackgroundImage(kFaviconColor));
200
201 EXPECT_EQ(kArtworkColor, GetBackgroundColor());
202 }
203
TEST_F(MediaNotificationBackgroundImplTest,DeriveBackgroundColor_SetAndRemoveArtworkWithFavicon)204 TEST_F(MediaNotificationBackgroundImplTest,
205 DeriveBackgroundColor_SetAndRemoveArtworkWithFavicon) {
206 constexpr SkColor kArtworkColor = SK_ColorYELLOW;
207 constexpr SkColor kFaviconColor = SK_ColorRED;
208
209 background()->UpdateArtwork(CreateTestBackgroundImage(kArtworkColor));
210 background()->UpdateFavicon(CreateTestBackgroundImage(kFaviconColor));
211 background()->UpdateArtwork(gfx::ImageSkia());
212
213 const SkColor expected_color = SkColorSetRGB(
214 SkColorGetR(kFaviconColor) * GetBackgroundFaviconColorShadeFactor(),
215 SkColorGetG(kFaviconColor) * GetBackgroundFaviconColorShadeFactor(),
216 SkColorGetB(kFaviconColor) * GetBackgroundFaviconColorShadeFactor());
217 EXPECT_EQ(expected_color, GetBackgroundColor());
218 }
219
TEST_F(MediaNotificationBackgroundImplTest,GetBackgroundColorRespectsTheme)220 TEST_F(MediaNotificationBackgroundImplTest, GetBackgroundColorRespectsTheme) {
221 TestDarkTheme dark_theme;
222 views::View owner;
223 owner.SetNativeThemeForTesting(&dark_theme);
224 EXPECT_EQ(kDarkBackgroundColor, background()->GetBackgroundColor(owner));
225 }
226
227 // MediaNotificationBackgroundImplBlackWhiteTest will repeat these tests with a
228 // parameter that is either black or white.
229 class MediaNotificationBackgroundImplBlackWhiteTest
230 : public MediaNotificationBackgroundImplTest,
231 public testing::WithParamInterface<SkColor> {
232 public:
IsBlack() const233 bool IsBlack() const { return GetParam() == SK_ColorBLACK; }
234
CreateTestForegroundArtwork(const SkColor & first,const SkColor & second,int first_width,int second_height)235 gfx::ImageSkia CreateTestForegroundArtwork(const SkColor& first,
236 const SkColor& second,
237 int first_width,
238 int second_height) {
239 gfx::Rect area(100, 100);
240
241 SkBitmap bitmap;
242 bitmap.allocN32Pixels(area.width(), area.height());
243 bitmap.eraseColor(GetParam());
244
245 area.Inset(40, 0, 0, 0);
246 bitmap.erase(first, gfx::RectToSkIRect(area));
247
248 area.Inset(first_width, area.height() - second_height, 0, 0);
249 bitmap.erase(second, gfx::RectToSkIRect(area));
250
251 return gfx::ImageSkia::CreateFrom1xBitmap(bitmap);
252 }
253 };
254
255 INSTANTIATE_TEST_SUITE_P(All,
256 MediaNotificationBackgroundImplBlackWhiteTest,
257 testing::Values(SK_ColorBLACK, SK_ColorWHITE));
258
259 // If the most popular color is black or white but there is no secondary color
260 // we should use the most popular color.
TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,DeriveBackgroundColor_PopularBlackWhiteNoSecondaryColor)261 TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,
262 DeriveBackgroundColor_PopularBlackWhiteNoSecondaryColor) {
263 background()->UpdateArtwork(CreateTestBackgroundImage(GetParam()));
264 EXPECT_EQ(GetParam(), GetBackgroundColor());
265 }
266
267 // If the most popular color is black or white and there is a secondary color
268 // that is very minor then we should use the most popular color.
TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,DeriveBackgroundColor_VeryPopularBlackWhite)269 TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,
270 DeriveBackgroundColor_VeryPopularBlackWhite) {
271 background()->UpdateArtwork(
272 CreateTestBackgroundImage(GetParam(), SK_ColorYELLOW, 20));
273 EXPECT_EQ(GetParam(), GetBackgroundColor());
274 }
275
276 // If the most popular color is black or white but it is not that popular then
277 // we should use the secondary color.
TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,DeriveBackgroundColor_NotVeryPopularBlackWhite)278 TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,
279 DeriveBackgroundColor_NotVeryPopularBlackWhite) {
280 constexpr SkColor kTestColor = SK_ColorYELLOW;
281 background()->UpdateArtwork(
282 CreateTestBackgroundImage(GetParam(), kTestColor, 40));
283 EXPECT_EQ(kTestColor, GetBackgroundColor());
284 }
285
286 // If there are multiple vibrant colors then the foreground color should be the
287 // most popular one.
TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,DeriveForegroundColor_Palette_MultiVibrant)288 TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,
289 DeriveForegroundColor_Palette_MultiVibrant) {
290 const SkColor kTestColor = SK_ColorCYAN;
291
292 background()->UpdateArtwork(CreateTestForegroundArtwork(
293 kTestColor, GetColorFromSL(kVibrantSaturation, kDarkLuma), 59,
294 kDefaultForegroundArtworkHeight));
295
296 EXPECT_EQ(GetParam(), GetBackgroundColor());
297 EXPECT_EQ(kTestColor, GetForegroundColor());
298 }
299
300 // If there is a vibrant and muted color then the foreground color should be the
301 // more vibrant one.
TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,DeriveForegroundColor_Palette_Vibrant)302 TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,
303 DeriveForegroundColor_Palette_Vibrant) {
304 const SkColor kTestColor = GetColorFromSL(kVibrantSaturation, kNormalLuma);
305
306 background()->UpdateArtwork(CreateTestForegroundArtwork(
307 kTestColor, GetColorFromSL(kMutedSaturation, kNormalLuma), 30,
308 kDefaultForegroundArtworkHeight));
309
310 EXPECT_EQ(GetParam(), GetBackgroundColor());
311 EXPECT_EQ(kTestColor, GetForegroundColor());
312 }
313
314 // If there are multiple muted colors then the foreground color should be the
315 // most popular one.
TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,DeriveForegroundColor_Palette_MultiMuted)316 TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,
317 DeriveForegroundColor_Palette_MultiMuted) {
318 const SkColor kTestColor = GetColorFromSL(kMutedSaturation, kNormalLuma);
319
320 background()->UpdateArtwork(CreateTestForegroundArtwork(
321 kTestColor, GetColorFromSL(kMutedSaturation, kDarkLuma), 59,
322 kDefaultForegroundArtworkHeight));
323
324 EXPECT_EQ(GetParam(), GetBackgroundColor());
325 EXPECT_EQ(kTestColor, GetForegroundColor());
326 }
327
328 // If there is a normal and light muted color then the foreground color should
329 // be the normal one.
TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,DeriveForegroundColor_Palette_Muted)330 TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,
331 DeriveForegroundColor_Palette_Muted) {
332 const SkColor kTestColor = GetColorFromSL(kMutedSaturation, kNormalLuma);
333 const SkColor kSecondColor =
334 GetColorFromSL(kMutedSaturation, IsBlack() ? kDarkLuma : kLightLuma);
335
336 background()->UpdateArtwork(CreateTestForegroundArtwork(
337 kTestColor, kSecondColor, 30, kDefaultForegroundArtworkHeight));
338
339 EXPECT_EQ(GetParam(), GetBackgroundColor());
340 EXPECT_EQ(kTestColor, GetForegroundColor());
341 }
342
343 // If the best color is not the most popular one, but the most popular one is
344 // not that popular then we should use the best color.
TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,DeriveForegroundColor_Palette_NotPopular)345 TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,
346 DeriveForegroundColor_Palette_NotPopular) {
347 const SkColor kTestColor = SK_ColorMAGENTA;
348
349 background()->UpdateArtwork(CreateTestForegroundArtwork(
350 kTestColor, GetColorFromSL(kMutedSaturation, kNormalLuma), 25,
351 kDefaultForegroundArtworkHeight));
352
353 EXPECT_EQ(GetParam(), GetBackgroundColor());
354 EXPECT_EQ(kTestColor, GetForegroundColor());
355 }
356
357 // If we do not have a best color but we have a popular one over a threshold
358 // then we should use that one.
TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,DeriveForegroundColor_MostPopular)359 TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,
360 DeriveForegroundColor_MostPopular) {
361 const SkColor kTestColor = GetColorFromSL(kMutedSaturation, kNormalLuma);
362
363 background()->UpdateArtwork(CreateTestForegroundArtwork(
364 kTestColor, GetColorFromSL(kVibrantSaturation, kNormalLuma), 59, 50));
365
366 EXPECT_EQ(GetParam(), GetBackgroundColor());
367 EXPECT_EQ(kTestColor, GetForegroundColor());
368 }
369
370 // If the background color is dark then we should select for a lighter color,
371 // otherwise we should select for a darker one.
TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,DeriveForegroundColor_Palette_MoreVibrant)372 TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,
373 DeriveForegroundColor_Palette_MoreVibrant) {
374 const SkColor kTestColor =
375 GetColorFromSL(kVibrantSaturation, IsBlack() ? kLightLuma : kDarkLuma);
376
377 background()->UpdateArtwork(CreateTestForegroundArtwork(
378 kTestColor, GetColorFromSL(kVibrantSaturation, kNormalLuma), 30,
379 kDefaultForegroundArtworkHeight));
380
381 EXPECT_EQ(GetParam(), GetBackgroundColor());
382 EXPECT_EQ(kTestColor, GetForegroundColor());
383 }
384
385 // If the background color is dark then we should select for a lighter color,
386 // otherwise we should select for a darker one.
TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,DeriveForegroundColor_Palette_MoreMuted)387 TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,
388 DeriveForegroundColor_Palette_MoreMuted) {
389 const SkColor kTestColor =
390 GetColorFromSL(kMutedSaturation, IsBlack() ? kLightLuma : kDarkLuma);
391 const SkColor kSecondColor =
392 GetColorFromSL(kMutedSaturation, IsBlack() ? kDarkLuma : kLightLuma);
393
394 background()->UpdateArtwork(CreateTestForegroundArtwork(
395 kTestColor, kSecondColor, 30, kDefaultForegroundArtworkHeight));
396
397 EXPECT_EQ(GetParam(), GetBackgroundColor());
398 EXPECT_EQ(kTestColor, GetForegroundColor());
399 }
400
401 // If we do not have any colors then we should use the fallback color based on
402 // the background color.
TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,DeriveForegroundColor_Fallback)403 TEST_P(MediaNotificationBackgroundImplBlackWhiteTest,
404 DeriveForegroundColor_Fallback) {
405 background()->UpdateArtwork(CreateTestForegroundArtwork(
406 SK_ColorTRANSPARENT, SK_ColorTRANSPARENT, 0, 0));
407
408 EXPECT_EQ(GetParam(), GetBackgroundColor());
409 EXPECT_EQ(GetParam() == SK_ColorBLACK ? SK_ColorWHITE : SK_ColorBLACK,
410 GetForegroundColor());
411 }
412
413 // MediaNotificationBackgroundImplRTLTest will repeat these tests with RTL
414 // disabled and enabled.
415 class MediaNotificationBackgroundImplRTLTest
416 : public MediaNotificationBackgroundImplTest,
417 public testing::WithParamInterface<bool> {
418 public:
SetUp()419 void SetUp() override {
420 command_line_.GetProcessCommandLine()->AppendSwitchASCII(
421 switches::kForceUIDirection, GetParam() ? switches::kForceDirectionRTL
422 : switches::kForceDirectionLTR);
423
424 MediaNotificationBackgroundImplTest::SetUp();
425
426 ASSERT_EQ(IsRTL(), base::i18n::IsRTL());
427 }
428
IsRTL() const429 bool IsRTL() const { return GetParam(); }
430
431 private:
432 base::test::ScopedRestoreICUDefaultLocale scoped_locale_;
433 base::test::ScopedCommandLine command_line_;
434 };
435
436 INSTANTIATE_TEST_SUITE_P(All,
437 MediaNotificationBackgroundImplRTLTest,
438 testing::Bool());
439
TEST_P(MediaNotificationBackgroundImplRTLTest,BoundsSanityCheck)440 TEST_P(MediaNotificationBackgroundImplRTLTest, BoundsSanityCheck) {
441 // The test notification will have a width of 200 and a height of 50.
442 gfx::Rect bounds(0, 0, 200, 50);
443 auto owner = std::make_unique<views::StaticSizedView>();
444 owner->SetBoundsRect(bounds);
445 ASSERT_EQ(bounds, owner->GetContentsBounds());
446
447 // Check the artwork is not visible by default.
448 EXPECT_EQ(0, background()->GetArtworkWidth(bounds.size()));
449 EXPECT_EQ(0, background()->GetArtworkVisibleWidth(bounds.size()));
450 EXPECT_EQ(gfx::Rect(IsRTL() ? 0 : 200, 0, 0, 50),
451 background()->GetArtworkBounds(*owner.get()));
452 EXPECT_EQ(gfx::Rect(IsRTL() ? 0 : 0, 0, 200, 50),
453 background()->GetFilledBackgroundBounds(*owner.get()));
454 EXPECT_EQ(gfx::Rect(0, 0, 0, 0),
455 background()->GetGradientBounds(*owner.get()));
456
457 // The background artwork image will have an aspect ratio of 2:1.
458 SkBitmap bitmap;
459 bitmap.allocN32Pixels(20, 10);
460 bitmap.eraseColor(SK_ColorWHITE);
461 background()->UpdateArtwork(gfx::ImageSkia::CreateFrom1xBitmap(bitmap));
462
463 // The artwork width will be 2x the height of the notification and the visible
464 // width will be limited to 10% the width of the notification.
465 EXPECT_EQ(100, background()->GetArtworkWidth(bounds.size()));
466 EXPECT_EQ(20, background()->GetArtworkVisibleWidth(bounds.size()));
467
468 // Update the visible width % to be greater than the width of the image.
469 background()->UpdateArtworkMaxWidthPct(0.6);
470 EXPECT_EQ(100, background()->GetArtworkVisibleWidth(bounds.size()));
471
472 // Check the artwork is positioned to the right.
473 EXPECT_EQ(gfx::Rect(IsRTL() ? 0 : 100, 0, 100, 50),
474 background()->GetArtworkBounds(*owner.get()));
475
476 // Check the filled background is to the left of the image.
477 EXPECT_EQ(gfx::Rect(IsRTL() ? 100 : 0, 0, 100, 50),
478 background()->GetFilledBackgroundBounds(*owner.get()));
479
480 // Check the gradient is positioned above the artwork.
481 const gfx::Rect gradient_bounds =
482 background()->GetGradientBounds(*owner.get());
483 EXPECT_EQ(gfx::Rect(IsRTL() ? 60 : 100, 0, 40, 50), gradient_bounds);
484
485 // Check the gradient point X-values are the start and end of
486 // |gradient_bounds|.
487 EXPECT_EQ(100, background()->GetGradientStartPoint(gradient_bounds).x());
488 EXPECT_EQ(IsRTL() ? 60 : 140,
489 background()->GetGradientEndPoint(gradient_bounds).x());
490
491 // Check both of the gradient point Y-values are half the height.
492 EXPECT_EQ(25, background()->GetGradientStartPoint(gradient_bounds).y());
493 EXPECT_EQ(25, background()->GetGradientEndPoint(gradient_bounds).y());
494 }
495
496 } // namespace media_message_center
497