OLD | NEW |
(Empty) | |
| 1 // Copyright (c) 2017 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/favicon/core/favicon_selector.h" |
| 6 |
| 7 #include <memory> |
| 8 #include <vector> |
| 9 |
| 10 #include "testing/gmock/include/gmock/gmock.h" |
| 11 #include "testing/gtest/include/gtest/gtest.h" |
| 12 |
| 13 namespace favicon { |
| 14 namespace { |
| 15 |
| 16 using favicon_base::FAVICON; |
| 17 using favicon_base::FaviconRawBitmapResult; |
| 18 using testing::ElementsAre; |
| 19 using testing::Eq; |
| 20 using testing::IsNull; |
| 21 using testing::Pointee; |
| 22 |
| 23 MATCHER_P(HasIconURL, expected_url, "") { |
| 24 *result_listener << "where icon URL is " << arg.icon_url; |
| 25 return arg.icon_url == GURL(expected_url); |
| 26 } |
| 27 |
| 28 MATCHER_P(HasValueWithIconURL, expected_url, "") { |
| 29 if (!arg) |
| 30 *result_listener << "where value is empty"; |
| 31 else |
| 32 *result_listener << "where value's icon URL is " << arg.value().icon_url; |
| 33 return arg.value().icon_url == GURL(expected_url); |
| 34 } |
| 35 |
| 36 std::vector<FaviconRawBitmapResult> CreateRawBitmapResults( |
| 37 const std::vector<gfx::Size>& sizes) { |
| 38 std::vector<FaviconRawBitmapResult> results; |
| 39 for (const gfx::Size& size : sizes) { |
| 40 FaviconRawBitmapResult bitmap_result; |
| 41 bitmap_result.bitmap_data = |
| 42 new base::RefCountedBytes(std::vector<unsigned char>(1U, 0U)); |
| 43 bitmap_result.pixel_size = size; |
| 44 CHECK(bitmap_result.is_valid()); |
| 45 results.push_back(bitmap_result); |
| 46 } |
| 47 return results; |
| 48 } |
| 49 |
| 50 std::vector<SkBitmap> CreateBitmaps(const std::vector<gfx::Size>& sizes) { |
| 51 std::vector<SkBitmap> bitmaps; |
| 52 for (const gfx::Size& size : sizes) { |
| 53 SkBitmap bmp; |
| 54 bmp.allocN32Pixels(size.width(), size.height()); |
| 55 bmp.eraseColor(SK_ColorRED); |
| 56 bitmaps.push_back(bmp); |
| 57 } |
| 58 return bitmaps; |
| 59 } |
| 60 |
| 61 TEST(FaviconSelectorTest, ShouldSortAndPruneForLargest) { |
| 62 const FaviconSelector::TargetSizeSpec spec = |
| 63 FaviconSelector::TargetSizeSpec::ForLargest(); |
| 64 |
| 65 const std::vector<gfx::Size> kEmptySizes; |
| 66 const std::vector<favicon::FaviconURL> kSourceIconURLs{ |
| 67 FaviconURL(GURL("http://www.google.com/a"), FAVICON, |
| 68 {gfx::Size(1, 1), gfx::Size(17, 17)}), |
| 69 FaviconURL(GURL("http://www.google.com/b"), FAVICON, |
| 70 {gfx::Size(1024, 1024), gfx::Size(512, 512)}), |
| 71 FaviconURL(GURL("http://www.google.com/c"), FAVICON, |
| 72 {gfx::Size(16, 16), gfx::Size(14, 14)}), |
| 73 FaviconURL(GURL("http://www.google.com/d"), FAVICON, kEmptySizes), |
| 74 FaviconURL(GURL("http://www.google.com/e"), FAVICON, kEmptySizes), |
| 75 FaviconURL(GURL("http://www.google.com/f"), FAVICON, |
| 76 {gfx::Size(10, 10), gfx::Size(400, 400)})}; |
| 77 |
| 78 EXPECT_THAT(spec.SortAndPruneCandidates(kSourceIconURLs), |
| 79 ElementsAre(HasIconURL("http://www.google.com/f"), |
| 80 HasIconURL("http://www.google.com/b"), |
| 81 HasIconURL("http://www.google.com/a"), |
| 82 HasIconURL("http://www.google.com/c"), |
| 83 // The rest of bitmaps come in order, there is no |
| 84 // sizes attribute. |
| 85 HasIconURL("http://www.google.com/d"), |
| 86 HasIconURL("http://www.google.com/e"))); |
| 87 } |
| 88 |
| 89 TEST(FaviconSelectorTest, ShouldSortAndPruneFor16x16) { |
| 90 // The last element is guaranteed to search for 16x16 pixels. |
| 91 const FaviconSelector::TargetSizeSpec spec = |
| 92 FaviconSelector::TargetSizeSpec::For16x16Dips().back(); |
| 93 ASSERT_EQ(16, spec.pixel_size()); |
| 94 |
| 95 const std::vector<gfx::Size> kEmptySizes; |
| 96 const std::vector<favicon::FaviconURL> kSourceIconURLs{ |
| 97 FaviconURL(GURL("http://www.google.com/a"), FAVICON, |
| 98 {gfx::Size(1, 1), gfx::Size(17, 17)}), |
| 99 FaviconURL(GURL("http://www.google.com/b"), FAVICON, |
| 100 {gfx::Size(1024, 1024), gfx::Size(512, 512)}), |
| 101 FaviconURL(GURL("http://www.google.com/c"), FAVICON, |
| 102 {gfx::Size(16, 16), gfx::Size(14, 14)}), |
| 103 FaviconURL(GURL("http://www.google.com/d"), FAVICON, kEmptySizes), |
| 104 FaviconURL(GURL("http://www.google.com/e"), FAVICON, kEmptySizes), |
| 105 FaviconURL(GURL("http://www.google.com/f"), FAVICON, |
| 106 {gfx::Size(10, 10), gfx::Size(400, 400)})}; |
| 107 |
| 108 EXPECT_THAT(spec.SortAndPruneCandidates(kSourceIconURLs), |
| 109 ElementsAre(HasIconURL("http://www.google.com/c"), |
| 110 HasIconURL("http://www.google.com/a"), |
| 111 HasIconURL("http://www.google.com/f"), |
| 112 HasIconURL("http://www.google.com/b"), |
| 113 // The rest of bitmaps come in order, there is no |
| 114 // sizes attribute. |
| 115 HasIconURL("http://www.google.com/d"), |
| 116 HasIconURL("http://www.google.com/e"))); |
| 117 } |
| 118 |
| 119 TEST(FaviconSelectorTest, ShouldReportSatisfyingResultForLargest) {} |
| 120 |
| 121 TEST(FaviconSelectorTest, ShouldReportSatisfyingResultFor16x16) { |
| 122 // The last element is guaranteed to search for 16x16 pixels. |
| 123 const FaviconSelector::TargetSizeSpec spec = |
| 124 FaviconSelector::TargetSizeSpec::For16x16Dips().back(); |
| 125 ASSERT_EQ(16, spec.pixel_size()); |
| 126 |
| 127 EXPECT_FALSE(spec.HasSatisfyingResult(std::vector<FaviconRawBitmapResult>())); |
| 128 EXPECT_FALSE( |
| 129 spec.HasSatisfyingResult(CreateRawBitmapResults({gfx::Size(15, 15)}))); |
| 130 EXPECT_FALSE( |
| 131 spec.HasSatisfyingResult(CreateRawBitmapResults({gfx::Size(17, 17)}))); |
| 132 EXPECT_FALSE(spec.HasSatisfyingResult( |
| 133 CreateRawBitmapResults({gfx::Size(15, 15), gfx::Size(17, 17)}))); |
| 134 |
| 135 EXPECT_TRUE( |
| 136 spec.HasSatisfyingResult(CreateRawBitmapResults({gfx::Size(16, 16)}))); |
| 137 EXPECT_TRUE(spec.HasSatisfyingResult(CreateRawBitmapResults( |
| 138 {gfx::Size(15, 15), gfx::Size(16, 16), gfx::Size(17, 17)}))); |
| 139 } |
| 140 |
| 141 TEST(FaviconSelectorTest, ShouldDequeueSortedForLargest) { |
| 142 const std::vector<gfx::Size> kEmptySizes; |
| 143 |
| 144 FaviconSelector selector( |
| 145 FaviconSelector::TargetSizeSpec::ForLargest(), |
| 146 {FaviconURL(GURL("http://www.google.com/a"), FAVICON, |
| 147 {gfx::Size(1, 1), gfx::Size(17, 17)}), |
| 148 FaviconURL(GURL("http://www.google.com/b"), FAVICON, |
| 149 {gfx::Size(1024, 1024), gfx::Size(512, 512)}), |
| 150 FaviconURL(GURL("http://www.google.com/c"), FAVICON, |
| 151 {gfx::Size(16, 16), gfx::Size(14, 14)}), |
| 152 FaviconURL(GURL("http://www.google.com/d"), FAVICON, kEmptySizes), |
| 153 FaviconURL(GURL("http://www.google.com/e"), FAVICON, kEmptySizes)}); |
| 154 |
| 155 EXPECT_THAT(selector.CurrentCandidate(), |
| 156 Pointee(HasIconURL("http://www.google.com/b"))); |
| 157 EXPECT_THAT(selector.DequeueCandidate(), |
| 158 HasValueWithIconURL("http://www.google.com/b")); |
| 159 EXPECT_THAT(selector.CurrentCandidate(), |
| 160 Pointee(HasIconURL("http://www.google.com/a"))); |
| 161 EXPECT_THAT(selector.DequeueCandidate(), |
| 162 HasValueWithIconURL("http://www.google.com/a")); |
| 163 EXPECT_THAT(selector.CurrentCandidate(), |
| 164 Pointee(HasIconURL("http://www.google.com/c"))); |
| 165 EXPECT_THAT(selector.DequeueCandidate(), |
| 166 HasValueWithIconURL("http://www.google.com/c")); |
| 167 EXPECT_THAT(selector.CurrentCandidate(), |
| 168 Pointee(HasIconURL("http://www.google.com/d"))); |
| 169 EXPECT_THAT(selector.DequeueCandidate(), |
| 170 HasValueWithIconURL("http://www.google.com/d")); |
| 171 EXPECT_THAT(selector.CurrentCandidate(), |
| 172 Pointee(HasIconURL("http://www.google.com/e"))); |
| 173 EXPECT_THAT(selector.DequeueCandidate(), |
| 174 HasValueWithIconURL("http://www.google.com/e")); |
| 175 EXPECT_THAT(selector.CurrentCandidate(), IsNull()); |
| 176 EXPECT_FALSE(selector.DequeueCandidate().has_value()); |
| 177 } |
| 178 |
| 179 TEST(FaviconSelectorTest, ShouldDequeueSortedFor16x16) { |
| 180 // The last element is guaranteed to search for 16x16 pixels. |
| 181 const FaviconSelector::TargetSizeSpec spec = |
| 182 FaviconSelector::TargetSizeSpec::For16x16Dips().back(); |
| 183 ASSERT_EQ(16, spec.pixel_size()); |
| 184 |
| 185 FaviconSelector selector( |
| 186 FaviconSelector::TargetSizeSpec::ForLargest(), |
| 187 {FaviconURL(GURL("http://www.google.com/a"), FAVICON, |
| 188 {gfx::Size(15, 15)}), |
| 189 FaviconURL(GURL("http://www.google.com/b"), FAVICON, |
| 190 {gfx::Size(14, 14), gfx::Size(16, 16)})}); |
| 191 |
| 192 EXPECT_THAT(selector.CurrentCandidate(), |
| 193 Pointee(HasIconURL("http://www.google.com/b"))); |
| 194 EXPECT_THAT(selector.DequeueCandidate(), |
| 195 HasValueWithIconURL("http://www.google.com/b")); |
| 196 EXPECT_THAT(selector.CurrentCandidate(), |
| 197 Pointee(HasIconURL("http://www.google.com/a"))); |
| 198 EXPECT_THAT(selector.DequeueCandidate(), |
| 199 HasValueWithIconURL("http://www.google.com/a")); |
| 200 EXPECT_THAT(selector.CurrentCandidate(), IsNull()); |
| 201 EXPECT_FALSE(selector.DequeueCandidate().has_value()); |
| 202 } |
| 203 |
| 204 TEST(FaviconSelectorTest, ShouldProcessDownloadedImage) { |
| 205 const GURL kIconURL1("http://www.google.com/a"); |
| 206 const GURL kIconURL2("http://www.google.com/b"); |
| 207 const GURL kIconURL3("http://www.google.com/c"); |
| 208 const GURL kIconURL4("http://www.google.com/d"); |
| 209 |
| 210 const std::vector<gfx::Size> kSizes1{gfx::Size(14, 14), gfx::Size(16, 16)}; |
| 211 const std::vector<gfx::Size> kSizes2{gfx::Size(15, 15)}; |
| 212 const std::vector<gfx::Size> kSizes3{gfx::Size(1, 1), gfx::Size(8, 8)}; |
| 213 const std::vector<gfx::Size> kSizes4{gfx::Size(2, 2), gfx::Size(4, 4)}; |
| 214 |
| 215 // The last element is guaranteed to search for 16x16 pixels. |
| 216 const FaviconSelector::TargetSizeSpec spec = |
| 217 FaviconSelector::TargetSizeSpec::For16x16Dips().back(); |
| 218 ASSERT_EQ(16, spec.pixel_size()); |
| 219 |
| 220 FaviconSelector selector(spec, {FaviconURL(kIconURL1, FAVICON, kSizes1), |
| 221 FaviconURL(kIconURL2, FAVICON, kSizes2)}); |
| 222 ASSERT_FALSE(selector.BestBitmap()); |
| 223 ASSERT_TRUE(selector.CurrentCandidate()); |
| 224 |
| 225 // Any downloaded image should be better than hypothetical future candidates. |
| 226 EXPECT_TRUE(selector.ProcessDownloadedImage(kIconURL3, FAVICON, |
| 227 CreateBitmaps(kSizes3), kSizes3)); |
| 228 ASSERT_TRUE(selector.BestBitmap()); |
| 229 EXPECT_THAT(selector.BestBitmap()->candidate.icon_url, Eq(kIconURL3)); |
| 230 EXPECT_THAT(selector.BestBitmap()->original_size, Eq(kSizes3[1])); |
| 231 |
| 232 // Feed in a worse bitmap. |
| 233 EXPECT_FALSE(selector.ProcessDownloadedImage( |
| 234 kIconURL4, FAVICON, CreateBitmaps(kSizes4), kSizes4)); |
| 235 ASSERT_TRUE(selector.BestBitmap()); |
| 236 EXPECT_THAT(selector.BestBitmap()->candidate.icon_url, Eq(kIconURL3)); |
| 237 EXPECT_THAT(selector.BestBitmap()->original_size, Eq(kSizes3[1])); |
| 238 |
| 239 // Feed in an even better bitmap, registered in the queue. We'll verify that |
| 240 // the candidate gets removed from the queue. |
| 241 ASSERT_TRUE(selector.CurrentCandidate()); |
| 242 ASSERT_THAT(selector.CurrentCandidate()->icon_url, Eq(kIconURL1)); |
| 243 EXPECT_TRUE(selector.ProcessDownloadedImage(kIconURL1, FAVICON, |
| 244 CreateBitmaps(kSizes1), kSizes1)); |
| 245 ASSERT_TRUE(selector.BestBitmap()); |
| 246 EXPECT_THAT(selector.BestBitmap()->candidate.icon_url, Eq(kIconURL1)); |
| 247 EXPECT_THAT(selector.BestBitmap()->original_size, Eq(kSizes1[1])); |
| 248 |
| 249 EXPECT_FALSE(selector.CurrentCandidate()); |
| 250 EXPECT_FALSE(selector.DequeueCandidate()); |
| 251 } |
| 252 |
| 253 } // namespace |
| 254 } // namespace favicon |
OLD | NEW |