Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 /* | 1 /* |
| 2 * Copyright 2012 Google Inc. | 2 * Copyright 2012 Google Inc. |
| 3 * | 3 * |
| 4 * Use of this source code is governed by a BSD-style license that can be | 4 * Use of this source code is governed by a BSD-style license that can be |
| 5 * found in the LICENSE file. | 5 * found in the LICENSE file. |
| 6 */ | 6 */ |
| 7 | 7 |
| 8 #include "PictureRenderer.h" | 8 #include "PictureRenderer.h" |
| 9 #include "picture_utils.h" | 9 #include "picture_utils.h" |
| 10 #include "SamplePipeControllers.h" | 10 #include "SamplePipeControllers.h" |
| (...skipping 30 matching lines...) Expand all Loading... | |
| 41 return SkScalarLog(x) * log2_conversion_factor; | 41 return SkScalarLog(x) * log2_conversion_factor; |
| 42 } | 42 } |
| 43 | 43 |
| 44 namespace sk_tools { | 44 namespace sk_tools { |
| 45 | 45 |
| 46 enum { | 46 enum { |
| 47 kDefaultTileWidth = 256, | 47 kDefaultTileWidth = 256, |
| 48 kDefaultTileHeight = 256 | 48 kDefaultTileHeight = 256 |
| 49 }; | 49 }; |
| 50 | 50 |
| 51 /* | |
| 52 * TODO(epoger): Make constant strings consistent instead of mixing hypenated an d camel-caps. | |
|
epoger
2014/05/07 03:15:16
moved to image_expectations
| |
| 53 * | |
| 54 * TODO(epoger): Similar constants are already maintained in 2 other places: | |
| 55 * gm/gm_json.py and gm/gm_expectations.cpp. We shouldn't add yet a third place. | |
| 56 * Figure out a way to share the definitions instead. | |
| 57 * | |
| 58 * Note that, as of https://codereview.chromium.org/226293002 , the JSON | |
| 59 * schema used here has started to differ from the one in gm_expectations.cpp . | |
| 60 * TODO(epoger): Consider getting GM and render_pictures to use the same JSON | |
| 61 * output module. | |
| 62 */ | |
| 63 const static char kJsonKey_ActualResults[] = "actual-results"; | |
| 64 const static char kJsonKey_Header[] = "header"; | |
| 65 const static char kJsonKey_Header_Type[] = "type"; | |
| 66 const static char kJsonKey_Header_Revision[] = "revision"; // unique within Typ e | |
| 67 const static char kJsonKey_Image_ChecksumAlgorithm[] = "checksumAlgorithm"; | |
| 68 const static char kJsonKey_Image_ChecksumValue[] = "checksumValue"; | |
| 69 const static char kJsonKey_Image_ComparisonResult[] = "comparisonResult"; | |
| 70 const static char kJsonKey_Image_Filepath[] = "filepath"; | |
| 71 const static char kJsonKey_Source_TiledImages[] = "tiled-images"; | |
| 72 const static char kJsonKey_Source_WholeImage[] = "whole-image"; | |
| 73 // Values (not keys) that are written out by this JSON generator | |
| 74 const static char kJsonValue_Header_Type[] = "ChecksummedImages"; | |
| 75 const static int kJsonValue_Header_Revision = 1; | |
| 76 const static char kJsonValue_Image_ChecksumAlgorithm_Bitmap64bitMD5[] = "bitmap- 64bitMD5"; | |
| 77 const static char kJsonValue_Image_ComparisonResult_NoComparison[] = "no-compari son"; | |
| 78 | |
| 79 void ImageResultsSummary::add(const char *sourceName, const char *fileName, uint 64_t hash, | |
| 80 const int *tileNumber) { | |
| 81 Json::Value image; | |
| 82 image[kJsonKey_Image_ChecksumAlgorithm] = kJsonValue_Image_ChecksumAlgorithm _Bitmap64bitMD5; | |
| 83 image[kJsonKey_Image_ChecksumValue] = Json::UInt64(hash); | |
| 84 image[kJsonKey_Image_ComparisonResult] = kJsonValue_Image_ComparisonResult_N oComparison; | |
| 85 image[kJsonKey_Image_Filepath] = fileName; | |
| 86 if (NULL == tileNumber) { | |
| 87 fActualResults[sourceName][kJsonKey_Source_WholeImage] = image; | |
| 88 } else { | |
| 89 fActualResults[sourceName][kJsonKey_Source_TiledImages][*tileNumber] = i mage; | |
| 90 } | |
| 91 } | |
| 92 | |
| 93 void ImageResultsSummary::add(const char *sourceName, const char *fileName, cons t SkBitmap& bitmap, | |
| 94 const int *tileNumber) { | |
| 95 uint64_t hash; | |
| 96 SkAssertResult(SkBitmapHasher::ComputeDigest(bitmap, &hash)); | |
| 97 this->add(sourceName, fileName, hash, tileNumber); | |
| 98 } | |
| 99 | |
| 100 void ImageResultsSummary::writeToFile(const char *filename) { | |
| 101 Json::Value header; | |
| 102 header[kJsonKey_Header_Type] = kJsonValue_Header_Type; | |
| 103 header[kJsonKey_Header_Revision] = kJsonValue_Header_Revision; | |
| 104 Json::Value root; | |
| 105 root[kJsonKey_Header] = header; | |
| 106 root[kJsonKey_ActualResults] = fActualResults; | |
| 107 std::string jsonStdString = root.toStyledString(); | |
| 108 SkFILEWStream stream(filename); | |
| 109 stream.write(jsonStdString.c_str(), jsonStdString.length()); | |
| 110 } | |
| 111 | |
| 112 void PictureRenderer::init(SkPicture* pict, const SkString* outputDir, | 51 void PictureRenderer::init(SkPicture* pict, const SkString* outputDir, |
| 113 const SkString* inputFilename, bool useChecksumBasedF ilenames) { | 52 const SkString* inputFilename, bool useChecksumBasedF ilenames) { |
| 114 this->CopyString(&fOutputDir, outputDir); | 53 this->CopyString(&fOutputDir, outputDir); |
| 115 this->CopyString(&fInputFilename, inputFilename); | 54 this->CopyString(&fInputFilename, inputFilename); |
| 116 fUseChecksumBasedFilenames = useChecksumBasedFilenames; | 55 fUseChecksumBasedFilenames = useChecksumBasedFilenames; |
| 117 | 56 |
| 118 SkASSERT(NULL == fPicture); | 57 SkASSERT(NULL == fPicture); |
| 119 SkASSERT(NULL == fCanvas.get()); | 58 SkASSERT(NULL == fCanvas.get()); |
| 120 if (NULL != fPicture || NULL != fCanvas.get()) { | 59 if (NULL != fPicture || NULL != fCanvas.get()) { |
| 121 return; | 60 return; |
| (...skipping 216 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 338 static bool write(SkCanvas* canvas, const SkString& outputDir, const SkString& i nputFilename, | 277 static bool write(SkCanvas* canvas, const SkString& outputDir, const SkString& i nputFilename, |
| 339 ImageResultsSummary *jsonSummaryPtr, bool useChecksumBasedFile names, | 278 ImageResultsSummary *jsonSummaryPtr, bool useChecksumBasedFile names, |
| 340 const int* tileNumberPtr=NULL) { | 279 const int* tileNumberPtr=NULL) { |
| 341 SkASSERT(canvas != NULL); | 280 SkASSERT(canvas != NULL); |
| 342 if (NULL == canvas) { | 281 if (NULL == canvas) { |
| 343 return false; | 282 return false; |
| 344 } | 283 } |
| 345 | 284 |
| 346 SkBitmap bitmap; | 285 SkBitmap bitmap; |
| 347 SkISize size = canvas->getDeviceSize(); | 286 SkISize size = canvas->getDeviceSize(); |
| 348 sk_tools::setup_bitmap(&bitmap, size.width(), size.height()); | 287 setup_bitmap(&bitmap, size.width(), size.height()); |
| 349 | |
| 350 // Make sure we only compute the bitmap hash once (at most). | |
| 351 uint64_t hash; | |
| 352 bool generatedHash = false; | |
| 353 | 288 |
| 354 canvas->readPixels(&bitmap, 0, 0); | 289 canvas->readPixels(&bitmap, 0, 0); |
| 355 sk_tools::force_all_opaque(bitmap); | 290 force_all_opaque(bitmap); |
| 291 BitmapAndDigest bitmapAndDigest(bitmap); | |
| 356 | 292 |
| 357 SkString escapedInputFilename(inputFilename); | 293 SkString escapedInputFilename(inputFilename); |
| 358 replace_char(&escapedInputFilename, '.', '_'); | 294 replace_char(&escapedInputFilename, '.', '_'); |
| 359 | 295 |
| 360 // TODO(epoger): what about including the config type within outputFilename? That way, | 296 // TODO(epoger): what about including the config type within outputFilename? That way, |
| 361 // we could combine results of different config types without conflicting fi lenames. | 297 // we could combine results of different config types without conflicting fi lenames. |
| 362 SkString outputFilename; | 298 SkString outputFilename; |
| 299 const ImageDigest *imageDigestPtr = bitmapAndDigest.getImageDigestPtr(); | |
| 363 const char *outputSubdirPtr = NULL; | 300 const char *outputSubdirPtr = NULL; |
| 364 if (useChecksumBasedFilenames) { | 301 if (useChecksumBasedFilenames) { |
| 365 SkASSERT(!generatedHash); | |
| 366 SkAssertResult(SkBitmapHasher::ComputeDigest(bitmap, &hash)); | |
| 367 generatedHash = true; | |
| 368 | |
| 369 outputSubdirPtr = escapedInputFilename.c_str(); | 302 outputSubdirPtr = escapedInputFilename.c_str(); |
| 370 outputFilename.set(kJsonValue_Image_ChecksumAlgorithm_Bitmap64bitMD5); | 303 outputFilename.set(imageDigestPtr->getHashType()); |
| 371 outputFilename.append("_"); | 304 outputFilename.append("_"); |
| 372 outputFilename.appendU64(hash); | 305 outputFilename.appendU64(imageDigestPtr->getHashValue()); |
| 373 } else { | 306 } else { |
| 374 outputFilename.set(escapedInputFilename); | 307 outputFilename.set(escapedInputFilename); |
| 375 if (NULL != tileNumberPtr) { | 308 if (NULL != tileNumberPtr) { |
| 376 outputFilename.append("-tile"); | 309 outputFilename.append("-tile"); |
| 377 outputFilename.appendS32(*tileNumberPtr); | 310 outputFilename.appendS32(*tileNumberPtr); |
| 378 } | 311 } |
| 379 } | 312 } |
| 380 outputFilename.append(".png"); | 313 outputFilename.append(".png"); |
| 381 | 314 |
| 382 if (NULL != jsonSummaryPtr) { | 315 if (NULL != jsonSummaryPtr) { |
| 383 if (!generatedHash) { | 316 const ImageDigest *imageDigestPtr = bitmapAndDigest.getImageDigestPtr(); |
| 384 SkAssertResult(SkBitmapHasher::ComputeDigest(bitmap, &hash)); | |
| 385 generatedHash = true; | |
| 386 } | |
| 387 | |
| 388 SkString outputRelativePath; | 317 SkString outputRelativePath; |
| 389 if (outputSubdirPtr) { | 318 if (outputSubdirPtr) { |
| 390 outputRelativePath.set(outputSubdirPtr); | 319 outputRelativePath.set(outputSubdirPtr); |
| 391 outputRelativePath.append("/"); // always use "/", even on Windows | 320 outputRelativePath.append("/"); // always use "/", even on Windows |
| 392 outputRelativePath.append(outputFilename); | 321 outputRelativePath.append(outputFilename); |
| 393 } else { | 322 } else { |
| 394 outputRelativePath.set(outputFilename); | 323 outputRelativePath.set(outputFilename); |
| 395 } | 324 } |
| 396 | 325 |
| 397 jsonSummaryPtr->add(inputFilename.c_str(), outputRelativePath.c_str(), | 326 jsonSummaryPtr->add(inputFilename.c_str(), outputRelativePath.c_str(), |
| 398 hash, tileNumberPtr); | 327 *imageDigestPtr, tileNumberPtr); |
| 399 } | 328 } |
| 400 | 329 |
| 401 if (outputDir.isEmpty()) { | 330 if (outputDir.isEmpty()) { |
| 402 return true; | 331 return true; |
| 403 } | 332 } |
| 404 | 333 |
| 405 SkString dirPath; | 334 SkString dirPath; |
| 406 if (outputSubdirPtr) { | 335 if (outputSubdirPtr) { |
| 407 dirPath = SkOSPath::SkPathJoin(outputDir.c_str(), outputSubdirPtr); | 336 dirPath = SkOSPath::SkPathJoin(outputDir.c_str(), outputSubdirPtr); |
| 408 sk_mkdir(dirPath.c_str()); | 337 sk_mkdir(dirPath.c_str()); |
| (...skipping 603 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1012 virtual SkString getConfigNameInternal() SK_OVERRIDE { | 941 virtual SkString getConfigNameInternal() SK_OVERRIDE { |
| 1013 return SkString("picture_clone"); | 942 return SkString("picture_clone"); |
| 1014 } | 943 } |
| 1015 }; | 944 }; |
| 1016 | 945 |
| 1017 PictureRenderer* CreatePictureCloneRenderer() { | 946 PictureRenderer* CreatePictureCloneRenderer() { |
| 1018 return SkNEW(PictureCloneRenderer); | 947 return SkNEW(PictureCloneRenderer); |
| 1019 } | 948 } |
| 1020 | 949 |
| 1021 } // namespace sk_tools | 950 } // namespace sk_tools |
| OLD | NEW |