OLD | NEW |
1 // Copyright 2012 The Chromium Authors. All rights reserved. | 1 // Copyright 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 "ios/chrome/browser/webp_transcode/webp_decoder.h" | 5 #include "ios/chrome/browser/webp_transcode/webp_decoder.h" |
6 | 6 |
7 #import <CoreGraphics/CoreGraphics.h> | 7 #import <CoreGraphics/CoreGraphics.h> |
8 #import <Foundation/Foundation.h> | 8 #import <Foundation/Foundation.h> |
9 #include <stddef.h> | 9 #include <stddef.h> |
10 #include <stdint.h> | 10 #include <stdint.h> |
11 | 11 |
12 #include <memory> | 12 #include <memory> |
13 | 13 |
14 #include "base/base_paths.h" | 14 #include "base/base_paths.h" |
15 #include "base/files/file_path.h" | 15 #include "base/files/file_path.h" |
16 #include "base/ios/ios_util.h" | 16 #include "base/ios/ios_util.h" |
17 #include "base/logging.h" | 17 #include "base/logging.h" |
18 #include "base/mac/scoped_cftyperef.h" | 18 #include "base/mac/scoped_cftyperef.h" |
19 #include "base/mac/scoped_nsobject.h" | 19 #include "base/mac/scoped_nsobject.h" |
20 #include "base/macros.h" | 20 #include "base/macros.h" |
21 #include "base/memory/ref_counted.h" | 21 #include "base/memory/ref_counted.h" |
22 #include "base/path_service.h" | 22 #include "base/path_service.h" |
23 #include "base/strings/sys_string_conversions.h" | 23 #include "base/strings/sys_string_conversions.h" |
24 #include "build/build_config.h" | 24 #include "build/build_config.h" |
25 #include "testing/gmock/include/gmock/gmock.h" | 25 #include "testing/gmock/include/gmock/gmock.h" |
26 #include "testing/gtest/include/gtest/gtest.h" | 26 #include "testing/gtest/include/gtest/gtest.h" |
27 | 27 |
| 28 #if !defined(__has_feature) || !__has_feature(objc_arc) |
| 29 #error "This file requires ARC support." |
| 30 #endif |
| 31 |
28 namespace webp_transcode { | 32 namespace webp_transcode { |
29 namespace { | 33 namespace { |
30 | 34 |
31 class WebpDecoderDelegate : public WebpDecoder::Delegate { | 35 class WebpDecoderDelegate : public WebpDecoder::Delegate { |
32 public: | 36 public: |
33 WebpDecoderDelegate() : image_([[NSMutableData alloc] init]) {} | 37 WebpDecoderDelegate() : image_([[NSMutableData alloc] init]) {} |
34 | 38 |
35 NSData* GetImage() const { return image_; } | 39 NSData* GetImage() const { return image_; } |
36 | 40 |
37 // WebpDecoder::Delegate methods. | 41 // WebpDecoder::Delegate methods. |
(...skipping 126 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
164 } // namespace | 168 } // namespace |
165 | 169 |
166 TEST_F(WebpDecoderTest, DecodeToJpeg) { | 170 TEST_F(WebpDecoderTest, DecodeToJpeg) { |
167 // TODO(droger): This test fails on iOS 9 x64 devices. http://crbug.com/523235 | 171 // TODO(droger): This test fails on iOS 9 x64 devices. http://crbug.com/523235 |
168 #if defined(OS_IOS) && defined(ARCH_CPU_ARM64) && !TARGET_IPHONE_SIMULATOR | 172 #if defined(OS_IOS) && defined(ARCH_CPU_ARM64) && !TARGET_IPHONE_SIMULATOR |
169 if (base::ios::IsRunningOnIOS9OrLater()) | 173 if (base::ios::IsRunningOnIOS9OrLater()) |
170 return; | 174 return; |
171 #endif | 175 #endif |
172 // Load a WebP image from disk. | 176 // Load a WebP image from disk. |
173 base::scoped_nsobject<NSData> webp_image( | 177 base::scoped_nsobject<NSData> webp_image( |
174 [LoadImage(base::FilePath("test.webp")) retain]); | 178 LoadImage(base::FilePath("test.webp"))); |
175 ASSERT_TRUE(webp_image != nil); | 179 ASSERT_TRUE(webp_image != nil); |
176 // Load reference image. | 180 // Load reference image. |
177 base::scoped_nsobject<NSData> jpg_image( | 181 base::scoped_nsobject<NSData> jpg_image( |
178 [LoadImage(base::FilePath("test.jpg")) retain]); | 182 LoadImage(base::FilePath("test.jpg"))); |
179 ASSERT_TRUE(jpg_image != nil); | 183 ASSERT_TRUE(jpg_image != nil); |
180 // Convert to JPEG. | 184 // Convert to JPEG. |
181 EXPECT_CALL(*delegate_, OnFinishedDecoding(true)).Times(1); | 185 EXPECT_CALL(*delegate_, OnFinishedDecoding(true)).Times(1); |
182 EXPECT_CALL(*delegate_, SetImageFeatures(testing::_, WebpDecoder::JPEG)) | 186 EXPECT_CALL(*delegate_, SetImageFeatures(testing::_, WebpDecoder::JPEG)) |
183 .Times(1); | 187 .Times(1); |
184 decoder_->OnDataReceived(webp_image); | 188 decoder_->OnDataReceived(webp_image); |
185 // Compare to reference image. | 189 // Compare to reference image. |
186 EXPECT_TRUE(CheckCompressedImagesEqual(jpg_image, delegate_->GetImage(), | 190 EXPECT_TRUE(CheckCompressedImagesEqual(jpg_image, delegate_->GetImage(), |
187 WebpDecoder::JPEG)); | 191 WebpDecoder::JPEG)); |
188 } | 192 } |
189 | 193 |
190 TEST_F(WebpDecoderTest, DecodeToPng) { | 194 TEST_F(WebpDecoderTest, DecodeToPng) { |
191 // TODO(droger): This test fails on iOS 9 x64 devices. http://crbug.com/523235 | 195 // TODO(droger): This test fails on iOS 9 x64 devices. http://crbug.com/523235 |
192 #if defined(OS_IOS) && defined(ARCH_CPU_ARM64) && !TARGET_IPHONE_SIMULATOR | 196 #if defined(OS_IOS) && defined(ARCH_CPU_ARM64) && !TARGET_IPHONE_SIMULATOR |
193 if (base::ios::IsRunningOnIOS9OrLater()) | 197 if (base::ios::IsRunningOnIOS9OrLater()) |
194 return; | 198 return; |
195 #endif | 199 #endif |
196 // Load a WebP image from disk. | 200 // Load a WebP image from disk. |
197 base::scoped_nsobject<NSData> webp_image( | 201 base::scoped_nsobject<NSData> webp_image( |
198 [LoadImage(base::FilePath("test_alpha.webp")) retain]); | 202 LoadImage(base::FilePath("test_alpha.webp"))); |
199 ASSERT_TRUE(webp_image != nil); | 203 ASSERT_TRUE(webp_image != nil); |
200 // Load reference image. | 204 // Load reference image. |
201 base::scoped_nsobject<NSData> png_image( | 205 base::scoped_nsobject<NSData> png_image( |
202 [LoadImage(base::FilePath("test_alpha.png")) retain]); | 206 LoadImage(base::FilePath("test_alpha.png"))); |
203 ASSERT_TRUE(png_image != nil); | 207 ASSERT_TRUE(png_image != nil); |
204 // Convert to PNG. | 208 // Convert to PNG. |
205 EXPECT_CALL(*delegate_, OnFinishedDecoding(true)).Times(1); | 209 EXPECT_CALL(*delegate_, OnFinishedDecoding(true)).Times(1); |
206 EXPECT_CALL(*delegate_, SetImageFeatures(testing::_, WebpDecoder::PNG)) | 210 EXPECT_CALL(*delegate_, SetImageFeatures(testing::_, WebpDecoder::PNG)) |
207 .Times(1); | 211 .Times(1); |
208 decoder_->OnDataReceived(webp_image); | 212 decoder_->OnDataReceived(webp_image); |
209 // Compare to reference image. | 213 // Compare to reference image. |
210 EXPECT_TRUE(CheckCompressedImagesEqual(png_image, delegate_->GetImage(), | 214 EXPECT_TRUE(CheckCompressedImagesEqual(png_image, delegate_->GetImage(), |
211 WebpDecoder::PNG)); | 215 WebpDecoder::PNG)); |
212 } | 216 } |
213 | 217 |
214 TEST_F(WebpDecoderTest, DecodeToTiff) { | 218 TEST_F(WebpDecoderTest, DecodeToTiff) { |
215 // TODO(droger): This test fails on iOS 9 x64 devices. http://crbug.com/523235 | 219 // TODO(droger): This test fails on iOS 9 x64 devices. http://crbug.com/523235 |
216 #if defined(OS_IOS) && defined(ARCH_CPU_ARM64) && !TARGET_IPHONE_SIMULATOR | 220 #if defined(OS_IOS) && defined(ARCH_CPU_ARM64) && !TARGET_IPHONE_SIMULATOR |
217 if (base::ios::IsRunningOnIOS9OrLater()) | 221 if (base::ios::IsRunningOnIOS9OrLater()) |
218 return; | 222 return; |
219 #endif | 223 #endif |
220 // Load a WebP image from disk. | 224 // Load a WebP image from disk. |
221 base::scoped_nsobject<NSData> webp_image( | 225 base::scoped_nsobject<NSData> webp_image( |
222 [LoadImage(base::FilePath("test_small.webp")) retain]); | 226 LoadImage(base::FilePath("test_small.webp"))); |
223 ASSERT_TRUE(webp_image != nil); | 227 ASSERT_TRUE(webp_image != nil); |
224 // Load reference image. | 228 // Load reference image. |
225 base::scoped_nsobject<NSData> tiff_image( | 229 base::scoped_nsobject<NSData> tiff_image( |
226 [LoadImage(base::FilePath("test_small.tiff")) retain]); | 230 LoadImage(base::FilePath("test_small.tiff"))); |
227 ASSERT_TRUE(tiff_image != nil); | 231 ASSERT_TRUE(tiff_image != nil); |
228 // Convert to TIFF. | 232 // Convert to TIFF. |
229 EXPECT_CALL(*delegate_, OnFinishedDecoding(true)).Times(1); | 233 EXPECT_CALL(*delegate_, OnFinishedDecoding(true)).Times(1); |
230 EXPECT_CALL(*delegate_, | 234 EXPECT_CALL(*delegate_, |
231 SetImageFeatures([tiff_image length], WebpDecoder::TIFF)) | 235 SetImageFeatures([tiff_image length], WebpDecoder::TIFF)) |
232 .Times(1); | 236 .Times(1); |
233 decoder_->OnDataReceived(webp_image); | 237 decoder_->OnDataReceived(webp_image); |
234 // Compare to reference image. | 238 // Compare to reference image. |
235 EXPECT_TRUE(CheckTiffImagesEqual(tiff_image, delegate_->GetImage())); | 239 EXPECT_TRUE(CheckTiffImagesEqual(tiff_image, delegate_->GetImage())); |
236 } | 240 } |
237 | 241 |
238 TEST_F(WebpDecoderTest, StreamedDecode) { | 242 TEST_F(WebpDecoderTest, StreamedDecode) { |
239 // TODO(droger): This test fails on iOS 9 x64 devices. http://crbug.com/523235 | 243 // TODO(droger): This test fails on iOS 9 x64 devices. http://crbug.com/523235 |
240 #if defined(OS_IOS) && defined(ARCH_CPU_ARM64) && !TARGET_IPHONE_SIMULATOR | 244 #if defined(OS_IOS) && defined(ARCH_CPU_ARM64) && !TARGET_IPHONE_SIMULATOR |
241 if (base::ios::IsRunningOnIOS9OrLater()) | 245 if (base::ios::IsRunningOnIOS9OrLater()) |
242 return; | 246 return; |
243 #endif | 247 #endif |
244 // Load a WebP image from disk. | 248 // Load a WebP image from disk. |
245 base::scoped_nsobject<NSData> webp_image( | 249 base::scoped_nsobject<NSData> webp_image( |
246 [LoadImage(base::FilePath("test.webp")) retain]); | 250 LoadImage(base::FilePath("test.webp"))); |
247 ASSERT_TRUE(webp_image != nil); | 251 ASSERT_TRUE(webp_image != nil); |
248 // Load reference image. | 252 // Load reference image. |
249 base::scoped_nsobject<NSData> jpg_image( | 253 base::scoped_nsobject<NSData> jpg_image( |
250 [LoadImage(base::FilePath("test.jpg")) retain]); | 254 LoadImage(base::FilePath("test.jpg"))); |
251 ASSERT_TRUE(jpg_image != nil); | 255 ASSERT_TRUE(jpg_image != nil); |
252 // Convert to JPEG in chunks. | 256 // Convert to JPEG in chunks. |
253 EXPECT_CALL(*delegate_, OnFinishedDecoding(true)).Times(1); | 257 EXPECT_CALL(*delegate_, OnFinishedDecoding(true)).Times(1); |
254 EXPECT_CALL(*delegate_, SetImageFeatures(testing::_, WebpDecoder::JPEG)) | 258 EXPECT_CALL(*delegate_, SetImageFeatures(testing::_, WebpDecoder::JPEG)) |
255 .Times(1); | 259 .Times(1); |
256 const size_t kChunkSize = 10; | 260 const size_t kChunkSize = 10; |
257 unsigned int num_chunks = 0; | 261 unsigned int num_chunks = 0; |
258 while ([webp_image length] > kChunkSize) { | 262 while ([webp_image length] > kChunkSize) { |
259 base::scoped_nsobject<NSData> chunk( | 263 base::scoped_nsobject<NSData> chunk( |
260 [[webp_image subdataWithRange:NSMakeRange(0, kChunkSize)] retain]); | 264 [webp_image subdataWithRange:NSMakeRange(0, kChunkSize)]); |
261 decoder_->OnDataReceived(chunk); | 265 decoder_->OnDataReceived(chunk); |
262 webp_image.reset([[webp_image | 266 webp_image.reset([webp_image |
263 subdataWithRange:NSMakeRange(kChunkSize, [webp_image length] - | 267 subdataWithRange:NSMakeRange(kChunkSize, |
264 kChunkSize)] retain]); | 268 [webp_image length] - kChunkSize)]); |
265 ++num_chunks; | 269 ++num_chunks; |
266 } | 270 } |
267 if ([webp_image length] > 0u) { | 271 if ([webp_image length] > 0u) { |
268 decoder_->OnDataReceived(webp_image); | 272 decoder_->OnDataReceived(webp_image); |
269 ++num_chunks; | 273 ++num_chunks; |
270 } | 274 } |
271 ASSERT_GT(num_chunks, 3u) << "Not enough chunks"; | 275 ASSERT_GT(num_chunks, 3u) << "Not enough chunks"; |
272 // Compare to reference image. | 276 // Compare to reference image. |
273 EXPECT_TRUE(CheckCompressedImagesEqual(jpg_image, delegate_->GetImage(), | 277 EXPECT_TRUE(CheckCompressedImagesEqual(jpg_image, delegate_->GetImage(), |
274 WebpDecoder::JPEG)); | 278 WebpDecoder::JPEG)); |
275 } | 279 } |
276 | 280 |
277 TEST_F(WebpDecoderTest, InvalidFormat) { | 281 TEST_F(WebpDecoderTest, InvalidFormat) { |
278 EXPECT_CALL(*delegate_, OnFinishedDecoding(false)).Times(1); | 282 EXPECT_CALL(*delegate_, OnFinishedDecoding(false)).Times(1); |
279 const char dummy_image[] = "(>'-')> <('-'<) ^('-')^ <('-'<) (>'-')>"; | 283 const char dummy_image[] = "(>'-')> <('-'<) ^('-')^ <('-'<) (>'-')>"; |
280 base::scoped_nsobject<NSData> data( | 284 base::scoped_nsobject<NSData> data( |
281 [[NSData alloc] initWithBytes:dummy_image length:arraysize(dummy_image)]); | 285 [[NSData alloc] initWithBytes:dummy_image length:arraysize(dummy_image)]); |
282 decoder_->OnDataReceived(data); | 286 decoder_->OnDataReceived(data); |
283 EXPECT_EQ(0u, [delegate_->GetImage() length]); | 287 EXPECT_EQ(0u, [delegate_->GetImage() length]); |
284 } | 288 } |
285 | 289 |
286 TEST_F(WebpDecoderTest, DecodeAborted) { | 290 TEST_F(WebpDecoderTest, DecodeAborted) { |
287 EXPECT_CALL(*delegate_, OnFinishedDecoding(false)).Times(1); | 291 EXPECT_CALL(*delegate_, OnFinishedDecoding(false)).Times(1); |
288 decoder_->Stop(); | 292 decoder_->Stop(); |
289 EXPECT_EQ(0u, [delegate_->GetImage() length]); | 293 EXPECT_EQ(0u, [delegate_->GetImage() length]); |
290 } | 294 } |
291 | 295 |
292 } // namespace webp_transcode | 296 } // namespace webp_transcode |
OLD | NEW |