294 {
296
298 }
299
300
301
302 auto runTest = [&](
const T&
src,
306 const bool csConversion =
308 const auto readCT = readInfo.colorType();
309 const auto readAT = readInfo.alphaType();
310 const auto srcCT = srcPixels.info().colorType();
311 const auto srcAT = srcPixels.info().alphaType();
313 const auto surfBounds =
SkIRect::MakeWH(srcPixels.width(), srcPixels.height());
315
316
317 const size_t dstRB = readBpp * readInfo.width() + 10 * readBpp;
318
319 const size_t dstSize = readInfo.computeByteSize(dstRB);
320 std::unique_ptr<char[]> dstData(new char[dstSize]);
321 SkPixmap dstPixels(readInfo, dstData.get(), dstRB);
322
323
324 static constexpr auto kInitialByte = static_cast<char>(0x1B);
325 std::fill_n(static_cast<char*>(dstPixels.writable_addr()),
326 dstPixels.computeByteSize(),
327 kInitialByte);
328
330
337 }
else if (!rules.fUncontainedRectSucceeds && !surfBounds.contains(
rect)) {
340
343 "Read failed. %sSrc CT: %s, Src AT: %s Read CT: %s, Read AT: %s, "
344 "Rect [%d, %d, %d, %d], CS conversion: %d\n",
349 }
351 }
352
353 bool guardOk = true;
354 auto guardCheck = [](
char x) {
return x == kInitialByte; };
355
356
357
361
362 const bool lumConversion =
365
366
367
368
369
370 float numer = (lumConversion || csConversion) ? 3.f : 2.f;
371
373 numer += 1;
374 }
376 float tol = (rgbBits == 0) ? 1.f : numer / ((1 << rgbBits) - 1);
377
378
379 float alphaTol = 1.f / ((1 << 10) - 1);
381
382
385 8});
386 alphaTol = (alphaBits == 0) ? 1.f : 2.f / ((1 << alphaBits) - 1);
387 }
388
389 const float tols[4] = {tol, tol, tol, alphaTol};
390 auto error = std::function<ComparePixmapsErrorReporter>([&](
int x,
int y,
391 const float diffs[4]) {
394 "%sSrc CT: %s, Src AT: %s, Read CT: %s, Read AT: %s, Rect [%d, %d, %d, %d]"
395 ", CS conversion: %d\n"
396 "Error at %d, %d. Diff in floats: (%f, %f, %f, %f)",
401 diffs[0], diffs[1], diffs[2], diffs[3]);
402 });
405 ref.alloc(refInfo);
407
408
410 ref.addr(),
411 ref.rowBytes());
413 srcPixels.addr(),
414 srcPixels.rowBytes());
415
416 unpremulSRc.readPixels(unpremulRef, srcReadRect.
x(), srcReadRect.
y());
417 } else {
418 srcPixels.readPixels(ref, srcReadRect.
x(), srcReadRect.
y());
419 }
420
424
425 const auto* v = dstData.get();
426 const auto*
end = dstData.get() + dstSize;
427 guardOk = std::all_of(v, v + dstWriteRect.
top() * dstPixels.rowBytes(), guardCheck);
428 v += dstWriteRect.
top() * dstPixels.rowBytes();
429 for (
int y = dstWriteRect.
top();
y < dstWriteRect.
bottom(); ++
y) {
430 guardOk |= std::all_of(v, v + dstWriteRect.
left() * readBpp, guardCheck);
431 auto pad = v + dstWriteRect.
right() * readBpp;
432 auto rowEnd =
std::min(
end, v + dstPixels.rowBytes());
433
434 guardOk |= std::all_of(pad, rowEnd, guardCheck);
435 v = rowEnd;
436 }
437 guardOk |= std::all_of(v,
end, guardCheck);
438 } else {
439 guardOk = std::all_of(dstData.get(), dstData.get() + dstSize, guardCheck);
440 }
441 if (!guardOk) {
443 "Result pixels modified result outside read rect [%d, %d, %d, %d]. "
444 "%sSrc CT: %s, Read CT: %s, CS conversion: %d",
447 csConversion);
448 }
450 };
451
452 static constexpr int kW = 16;
453 static constexpr int kH = 16;
454
457
458
459
460
461
462
463
464
465
466 std::array<bool, kLastEnum_SkColorType + 1> srcCTTestedThoroughly = {},
467 readCTTestedThoroughly = {};
471 continue;
472 }
476 continue;
477 }
478 if (rules.fSkip16BitCT &&
481 continue;
482 }
483
484
487 srcAT,
489
490
491
492
493
496
498
501 srcPixels.
alloc(srcInfo);
502 {
504
505
510 }
511 refPixels.readPixels(readPixmap, 0, 0);
512 }
513
514 auto src = srcFactory(srcPixels);
516 continue;
517 }
520 continue;
521 }
526 continue;
527 }
535
536 continue;
537 }
540 continue;
541 }
546 continue;
547 }
548 const auto& rects =
549 srcCTTestedThoroughly[sct] && readCTTestedThoroughly[rct]
550 ? shortRectArray
551 : longRectArray;
552 for (
const auto&
rect : rects) {
554 readCT, readAT, readCS);
556 Result r = runTest(
src, srcPixels, readInfo,
offset);
558 srcCTTestedThoroughly[sct] = true;
559 readCTTestedThoroughly[rct] = true;
560 }
561 }
562 }
563 }
564 }
565 }
566 }
567}
static constexpr GrColorType SkColorTypeToGrColorType(SkColorType ct)
std::vector< SkIRect > make_short_rect_array(int w, int h)
std::vector< SkIRect > make_long_rect_array(int w, int h)
@ kUnknown_SkAlphaType
uninitialized
@ kLastEnum_SkAlphaType
last valid value
@ kGray_SkColorChannelFlag
static uint32_t SkColorTypeChannelFlags(SkColorType ct)
static bool SkColorTypeIsAlphaOnly(SkColorType ct)
SK_API bool SkColorTypeIsAlwaysOpaque(SkColorType ct)
void alloc(const SkImageInfo &)
static bool Equals(const SkColorSpace *, const SkColorSpace *)
static sk_sp< SkColorSpace > MakeSRGBLinear()
const SkImageInfo & info() const
const void * addr() const
void append(const char text[])
const char * c_str() const
static float sat(float r, float g, float b)
constexpr int32_t x() const
constexpr int32_t y() const
bool intersect(const SkIRect &r)
static bool Intersects(const SkIRect &a, const SkIRect &b)
constexpr int32_t top() const
constexpr SkISize size() const
constexpr int32_t bottom() const
constexpr int32_t right() const
constexpr int32_t left() const
SkImageInfo makeAlphaType(SkAlphaType newAlphaType) const
SkImageInfo makeDimensions(SkISize newSize) const