180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru/*
380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru * Copyright 2011 Google Inc.
480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru *
580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru * Use of this source code is governed by a BSD-style license that can be
680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru * found in the LICENSE file.
780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru */
880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru#include "Test.h"
980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru#include "SkBitmap.h"
1080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru#include "SkCanvas.h"
1180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru#include "SkColorPriv.h"
1280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru#include "SkGradientShader.h"
1380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru#include "SkRect.h"
1480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
1580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Querustatic inline const char* boolStr(bool value) {
1680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    return value ? "true" : "false";
1780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru}
1880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
1980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru// these are in the same order as the SkBitmap::Config enum
2080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Querustatic const char* gConfigName[] = {
2180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    "None", "A1", "A8", "Index8", "565", "4444", "8888", "RLE_Index8"
2280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru};
2380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
2480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru/** Returns -1 on success, else the x coord of the first bad pixel, return its
2580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    value in bad
2680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru */
2780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Querutypedef int (*Proc)(const void*, int width, uint32_t expected, uint32_t* bad);
2880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
2980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Querustatic int proc_32(const void* ptr, int w, uint32_t expected, uint32_t* bad) {
3080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    const SkPMColor* addr = static_cast<const SkPMColor*>(ptr);
3180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    for (int x = 0; x < w; x++) {
3280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        if (addr[x] != expected) {
3380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            *bad = addr[x];
3480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            return x;
3580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        }
3680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    }
3780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    return -1;
3880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru}
3980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
4080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Querustatic int proc_16(const void* ptr, int w, uint32_t expected, uint32_t* bad) {
4180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    const uint16_t* addr = static_cast<const uint16_t*>(ptr);
4280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    for (int x = 0; x < w; x++) {
4380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        if (addr[x] != expected) {
4480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            *bad = addr[x];
4580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            return x;
4680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        }
4780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    }
4880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    return -1;
4980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru}
5080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
5180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Querustatic int proc_8(const void* ptr, int w, uint32_t expected, uint32_t* bad) {
5280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    const SkPMColor* addr = static_cast<const SkPMColor*>(ptr);
5380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    for (int x = 0; x < w; x++) {
5480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        if (SkGetPackedA32(addr[x]) != expected) {
5580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            *bad = SkGetPackedA32(addr[x]);
5680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            return x;
5780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        }
5880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    }
5980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    return -1;
6080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru}
6180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
62096defe64d408e54474fe19f418c95bf1a554fc7Derek Sollenbergerstatic int proc_bad(const void*, int, uint32_t, uint32_t* bad) {
6380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    *bad = 0;
6480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    return 0;
6580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru}
6680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
6780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Querustatic Proc find_proc(const SkBitmap& bm, SkPMColor expect32, uint16_t expect16,
6880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                      uint8_t expect8, uint32_t* expect) {
6980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    switch (bm.config()) {
7080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        case SkBitmap::kARGB_8888_Config:
7180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            *expect = expect32;
7280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            return proc_32;
7380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        case SkBitmap::kARGB_4444_Config:
7480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        case SkBitmap::kRGB_565_Config:
7580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            *expect = expect16;
7680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            return proc_16;
7780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        case SkBitmap::kA8_Config:
7880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            *expect = expect8;
7980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            return proc_8;
8080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        default:
8180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            *expect = 0;
8280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            return proc_bad;
8380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    }
8480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru}
8580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
8680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Querustatic bool check_color(const SkBitmap& bm, SkPMColor expect32,
8780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                        uint16_t expect16, uint8_t expect8,
8880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                        skiatest::Reporter* reporter) {
8980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    uint32_t expect;
9080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    Proc proc = find_proc(bm, expect32, expect16, expect8, &expect);
9180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    for (int y = 0; y < bm.height(); y++) {
9280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        uint32_t bad;
9380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        int x = proc(bm.getAddr(0, y), bm.width(), expect, &bad);
9480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        if (x >= 0) {
9580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            SkString str;
9680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            str.printf("BlitRow config=%s [%d %d] expected %x got %x",
9780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                       gConfigName[bm.config()], x, y, expect, bad);
9880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            reporter->reportFailed(str);
9980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            return false;
10080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        }
10180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    }
10280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    return true;
10380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru}
10480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
10580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru// Make sure our blits always map src==0 to a noop, and src==FF to full opaque
10680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Querustatic void test_00_FF(skiatest::Reporter* reporter) {
10780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    static const int W = 256;
10880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
10980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    static const SkBitmap::Config gDstConfig[] = {
11080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        SkBitmap::kARGB_8888_Config,
11180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        SkBitmap::kRGB_565_Config,
11280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru//        SkBitmap::kARGB_4444_Config,
11380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru//        SkBitmap::kA8_Config,
11480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    };
11580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
11680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    static const struct {
11780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        SkColor     fSrc;
11880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        SkColor     fDst;
11980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        SkPMColor   fResult32;
12080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        uint16_t    fResult16;
12180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        uint8_t     fResult8;
12280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    } gSrcRec[] = {
12380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        { 0,            0,          0,                                    0,      0 },
12480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        { 0,            0xFFFFFFFF, SkPackARGB32(0xFF, 0xFF, 0xFF, 0xFF), 0xFFFF, 0xFF },
12580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        { 0xFFFFFFFF,   0,          SkPackARGB32(0xFF, 0xFF, 0xFF, 0xFF), 0xFFFF, 0xFF },
12680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        { 0xFFFFFFFF,   0xFFFFFFFF, SkPackARGB32(0xFF, 0xFF, 0xFF, 0xFF), 0xFFFF, 0xFF },
12780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    };
12880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
12980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    SkPaint paint;
13080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
13180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    SkBitmap srcBM;
13280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    srcBM.setConfig(SkBitmap::kARGB_8888_Config, W, 1);
13380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    srcBM.allocPixels();
13480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
13580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    for (size_t i = 0; i < SK_ARRAY_COUNT(gDstConfig); i++) {
13680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        SkBitmap dstBM;
13780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        dstBM.setConfig(gDstConfig[i], W, 1);
13880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        dstBM.allocPixels();
13980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
14080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        SkCanvas canvas(dstBM);
14180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        for (size_t j = 0; j < SK_ARRAY_COUNT(gSrcRec); j++) {
14280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            srcBM.eraseColor(gSrcRec[j].fSrc);
14380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            dstBM.eraseColor(gSrcRec[j].fDst);
14480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
14580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            for (int k = 0; k < 4; k++) {
14680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                bool dither = (k & 1) != 0;
14780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                bool blend = (k & 2) != 0;
14880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                if (gSrcRec[j].fSrc != 0 && blend) {
14980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                    // can't make a numerical promise about blending anything
15080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                    // but 0
15180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                 //   continue;
15280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                }
15380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                paint.setDither(dither);
15480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                paint.setAlpha(blend ? 0x80 : 0xFF);
15580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                canvas.drawBitmap(srcBM, 0, 0, &paint);
15680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                if (!check_color(dstBM, gSrcRec[j].fResult32, gSrcRec[j].fResult16,
15780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                                 gSrcRec[j].fResult8, reporter)) {
15880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                    SkDebugf("--- src index %d dither %d blend %d\n", j, dither, blend);
15980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                }
16080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            }
16180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        }
16280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    }
16380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru}
16480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
16580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru///////////////////////////////////////////////////////////////////////////////
16680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
16780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Querustruct Mesh {
16880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    SkPoint     fPts[4];
16980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
17080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    Mesh(const SkBitmap& bm, SkPaint* paint) {
17180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        const SkScalar w = SkIntToScalar(bm.width());
17280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        const SkScalar h = SkIntToScalar(bm.height());
17380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        fPts[0].set(0, 0);
17480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        fPts[1].set(w, 0);
17580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        fPts[2].set(w, h);
17680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        fPts[3].set(0, h);
17780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        SkShader* s = SkShader::CreateBitmapShader(bm, SkShader::kClamp_TileMode,
17880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                                                   SkShader::kClamp_TileMode);
17980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        paint->setShader(s)->unref();
18080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
18180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    }
18280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
18380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    void draw(SkCanvas* canvas, SkPaint* paint) {
18480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        canvas->drawVertices(SkCanvas::kTriangleFan_VertexMode, 4, fPts, fPts,
18580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                             NULL, NULL, NULL, 0, *paint);
18680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    }
18780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru};
18880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
18980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru#include "SkImageEncoder.h"
19080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Querustatic void save_bm(const SkBitmap& bm, const char name[]) {
19180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    SkImageEncoder::EncodeFile(name, bm, SkImageEncoder::kPNG_Type, 100);
19280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru}
19380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
19480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Querustatic bool gOnce;
19580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
19680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru// Make sure our blits are invariant with the width of the blit (i.e. that
19780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru// special case for 8 at a time have the same results as narrower blits)
19880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Querustatic void test_diagonal(skiatest::Reporter* reporter) {
19980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    static const int W = 64;
20080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    static const int H = W;
20180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
20280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    static const SkBitmap::Config gDstConfig[] = {
20380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        SkBitmap::kARGB_8888_Config,
20480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        SkBitmap::kRGB_565_Config,
20580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        //        SkBitmap::kARGB_4444_Config,
20680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        //        SkBitmap::kA8_Config,
20780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    };
20880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
20980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    static const SkColor gDstBG[] = { 0, 0xFFFFFFFF };
21080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
21180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    SkPaint paint;
21280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
21380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    SkBitmap srcBM;
21480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    srcBM.setConfig(SkBitmap::kARGB_8888_Config, W, H);
21580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    srcBM.allocPixels();
21680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    SkRect srcR = {
21780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        0, 0, SkIntToScalar(srcBM.width()), SkIntToScalar(srcBM.height()) };
21880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
21980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    // cons up a mesh to draw the bitmap with
22080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    Mesh mesh(srcBM, &paint);
22180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
22280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    for (size_t i = 0; i < SK_ARRAY_COUNT(gDstConfig); i++) {
22380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        SkBitmap dstBM0, dstBM1;
22480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        dstBM0.setConfig(gDstConfig[i], W, H);
22580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        dstBM1.setConfig(gDstConfig[i], W, H);
22680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        dstBM0.allocPixels();
22780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        dstBM1.allocPixels();
22880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
22980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        SkCanvas canvas0(dstBM0);
23080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        SkCanvas canvas1(dstBM1);
23180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        SkColor bgColor;
23280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
23380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        for (size_t j = 0; j < SK_ARRAY_COUNT(gDstBG); j++) {
23480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            bgColor = gDstBG[j];
23580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
23680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            for (int c = 0; c <= 0xFF; c++) {
23780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                srcBM.eraseARGB(0xFF, c, c, c);
23880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
23980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                for (int k = 0; k < 4; k++) {
24080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                    bool dither = (k & 1) != 0;
24180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                    uint8_t alpha = (k & 2) ? 0x80 : 0xFF;
24280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                    paint.setDither(dither);
24380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                    paint.setAlpha(alpha);
24480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
24580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                    dstBM0.eraseColor(bgColor);
24680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                    dstBM1.eraseColor(bgColor);
24780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
24880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                    canvas0.drawRect(srcR, paint);
24980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                    mesh.draw(&canvas1, &paint);
25080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
25180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                    if (!gOnce && false) {
25280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                        save_bm(dstBM0, "drawBitmap.png");
25380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                        save_bm(dstBM1, "drawMesh.png");
25480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                        gOnce = true;
25580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                    }
25680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
25780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                    if (memcmp(dstBM0.getPixels(), dstBM1.getPixels(), dstBM0.getSize())) {
25880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                        SkString str;
25980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                        str.printf("Diagonal config=%s bg=0x%x dither=%d alpha=0x%x src=0x%x",
26080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                                   gConfigName[gDstConfig[i]], bgColor, dither, alpha, c);
26180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                        reporter->reportFailed(str);
26280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                    }
26380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru                }
26480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru            }
26580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru        }
26680bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    }
26780bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru}
26880bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
26980bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Querustatic void TestBlitRow(skiatest::Reporter* reporter) {
27080bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    test_00_FF(reporter);
27180bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru    test_diagonal(reporter);
27280bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru}
27380bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru
27480bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste Queru#include "TestClassDef.h"
27580bacfeb4bda06541e8695bd502229727bccfeaJean-Baptiste QueruDEFINE_TESTCLASS("BlitRow", TestBlitRowClass, TestBlitRow)
276