14bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com/*
24bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com * Copyright 2011 Google Inc.
34bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com *
44bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com * Use of this source code is governed by a BSD-style license that can be
54bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com * found in the LICENSE file.
64bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com */
74bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com
84bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com#include "gm.h"
94bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com#include "SkCanvas.h"
104bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com#include "SkColorPriv.h"
114bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com#include "SkShader.h"
124bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com
134bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com/*
144bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com *  Want to ensure that our bitmap sampler (in bitmap shader) keeps plenty of
154bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com *  precision when scaling very large images (where the dx might get very small.
164bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com */
174bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com
186005aeb3aa11e2dafb15000f5a1ba5c8c9af1fadreed@google.com#define W   257
196005aeb3aa11e2dafb15000f5a1ba5c8c9af1fadreed@google.com#define H   161
204bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com
214bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.comclass GiantBitmapGM : public skiagm::GM {
224bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com    SkBitmap* fBM;
234bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com    SkShader::TileMode fMode;
24b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.com    bool fDoFilter;
25b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.com    bool fDoRotate;
26ae933ce0ea5fd9d21cb6ef2cee7e729d32690aacrmistry@google.com
274bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com    const SkBitmap& getBitmap() {
284bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com        if (NULL == fBM) {
294bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com            fBM = new SkBitmap;
30eb9a46cbbb475e862a084aa2224ec18d4ac5e95breed@google.com            fBM->allocN32Pixels(W, H);
314bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com            fBM->eraseColor(SK_ColorWHITE);
324bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com
334bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com            const SkColor colors[] = {
344bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com                SK_ColorBLUE, SK_ColorRED, SK_ColorBLACK, SK_ColorGREEN
354bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com            };
364bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com
374bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com            SkCanvas canvas(*fBM);
384bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com            SkPaint paint;
394bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com            paint.setAntiAlias(true);
406005aeb3aa11e2dafb15000f5a1ba5c8c9af1fadreed@google.com            paint.setStrokeWidth(SkIntToScalar(20));
41ae933ce0ea5fd9d21cb6ef2cee7e729d32690aacrmistry@google.com
426005aeb3aa11e2dafb15000f5a1ba5c8c9af1fadreed@google.com#if 0
436005aeb3aa11e2dafb15000f5a1ba5c8c9af1fadreed@google.com            for (int y = -H*2; y < H; y += 50) {
444bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com                SkScalar yy = SkIntToScalar(y);
456005aeb3aa11e2dafb15000f5a1ba5c8c9af1fadreed@google.com                paint.setColor(colors[y/50 & 0x3]);
464bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com                canvas.drawLine(0, yy, SkIntToScalar(W), yy + SkIntToScalar(W),
474bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com                                paint);
484bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com            }
496005aeb3aa11e2dafb15000f5a1ba5c8c9af1fadreed@google.com#else
506005aeb3aa11e2dafb15000f5a1ba5c8c9af1fadreed@google.com            for (int x = -W; x < W; x += 60) {
516005aeb3aa11e2dafb15000f5a1ba5c8c9af1fadreed@google.com                paint.setColor(colors[x/60 & 0x3]);
526005aeb3aa11e2dafb15000f5a1ba5c8c9af1fadreed@google.com
536005aeb3aa11e2dafb15000f5a1ba5c8c9af1fadreed@google.com                SkScalar xx = SkIntToScalar(x);
546005aeb3aa11e2dafb15000f5a1ba5c8c9af1fadreed@google.com                canvas.drawLine(xx, 0, xx, SkIntToScalar(H),
556005aeb3aa11e2dafb15000f5a1ba5c8c9af1fadreed@google.com                                paint);
566005aeb3aa11e2dafb15000f5a1ba5c8c9af1fadreed@google.com            }
576005aeb3aa11e2dafb15000f5a1ba5c8c9af1fadreed@google.com#endif
584bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com        }
594bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com        return *fBM;
604bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com    }
614bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com
624bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.compublic:
63b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.com    GiantBitmapGM(SkShader::TileMode mode, bool doFilter, bool doRotate) : fBM(NULL) {
64b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.com        fMode = mode;
65b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.com        fDoFilter = doFilter;
66b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.com        fDoRotate = doRotate;
67b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.com    }
684bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com
694bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com    virtual ~GiantBitmapGM() {
704bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com        SkDELETE(fBM);
714bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com    }
724bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com
734bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.comprotected:
74a90c6803865766d28e92091f56f718f5e41fe80fcommit-bot@chromium.org    virtual uint32_t onGetFlags() const SK_OVERRIDE {
750c88d8233ba3a8baa9b4dd6ef515def6b3749980mtklein#ifdef SK_BUILD_FOR_ANDROID
760c88d8233ba3a8baa9b4dd6ef515def6b3749980mtklein        return kSkipTiled_Flag;
770c88d8233ba3a8baa9b4dd6ef515def6b3749980mtklein#else
78a90c6803865766d28e92091f56f718f5e41fe80fcommit-bot@chromium.org        if (fDoFilter && fDoRotate && fMode != SkShader::kClamp_TileMode) {
79a90c6803865766d28e92091f56f718f5e41fe80fcommit-bot@chromium.org            return kSkipTiled_Flag;
80a90c6803865766d28e92091f56f718f5e41fe80fcommit-bot@chromium.org        }
81a90c6803865766d28e92091f56f718f5e41fe80fcommit-bot@chromium.org        return 0;
820c88d8233ba3a8baa9b4dd6ef515def6b3749980mtklein#endif
83a90c6803865766d28e92091f56f718f5e41fe80fcommit-bot@chromium.org    }
84a90c6803865766d28e92091f56f718f5e41fe80fcommit-bot@chromium.org
854bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com    virtual SkString onShortName() {
864bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com        SkString str("giantbitmap_");
874bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com        switch (fMode) {
884bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com            case SkShader::kClamp_TileMode:
894bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com                str.append("clamp");
904bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com                break;
914bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com            case SkShader::kRepeat_TileMode:
924bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com                str.append("repeat");
934bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com                break;
944bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com            case SkShader::kMirror_TileMode:
954bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com                str.append("mirror");
964bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com                break;
974bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com            default:
984bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com                break;
994bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com        }
100b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.com        str.append(fDoFilter ? "_bilerp" : "_point");
101b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.com        str.append(fDoRotate ? "_rotate" : "_scale");
1024bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com        return str;
1034bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com    }
1044bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com
1054bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com    virtual SkISize onISize() { return SkISize::Make(640, 480); }
1064bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com
1074bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com    virtual void onDraw(SkCanvas* canvas) {
1084bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com        SkPaint paint;
109b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.com
1104bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com        SkMatrix m;
111b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.com        if (fDoRotate) {
112b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.com//            m.setRotate(SkIntToScalar(30), 0, 0);
113b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.com            m.setSkew(SK_Scalar1, 0, 0, 0);
1146005aeb3aa11e2dafb15000f5a1ba5c8c9af1fadreed@google.com//            m.postScale(2*SK_Scalar1/3, 2*SK_Scalar1/3);
115b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.com        } else {
1166005aeb3aa11e2dafb15000f5a1ba5c8c9af1fadreed@google.com            SkScalar scale = 11*SK_Scalar1/12;
1176005aeb3aa11e2dafb15000f5a1ba5c8c9af1fadreed@google.com            m.setScale(scale, scale);
118b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.com        }
1199c9005a347e9996f357bd79591bd34f74f8bbc66commit-bot@chromium.org        SkShader* s = SkShader::CreateBitmapShader(getBitmap(), fMode, fMode, &m);
120ae933ce0ea5fd9d21cb6ef2cee7e729d32690aacrmistry@google.com
1214bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com        paint.setShader(s)->unref();
1224469938e92d779dff05e745559e67907bbf21e78reed@google.com        paint.setFilterLevel(fDoFilter ? SkPaint::kLow_FilterLevel : SkPaint::kNone_FilterLevel);
1234bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com
124b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.com        canvas->translate(SkIntToScalar(50), SkIntToScalar(50));
125ae933ce0ea5fd9d21cb6ef2cee7e729d32690aacrmistry@google.com
12605af1afd429808913683da75644e48bece12e820humper@google.com//        SkRect r = SkRect::MakeXYWH(-50, -50, 32, 16);
1276005aeb3aa11e2dafb15000f5a1ba5c8c9af1fadreed@google.com//        canvas->drawRect(r, paint); return;
1284bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com        canvas->drawPaint(paint);
1294bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com    }
1304bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com
1314bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.comprivate:
1324bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com    typedef GM INHERITED;
1334bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com};
1344bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com
1354bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com///////////////////////////////////////////////////////////////////////////////
1364bc0a9db18d58698057b8f38a6f21537aca4ddcfreed@google.com
137b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GM* G000(void*) { return new GiantBitmapGM(SkShader::kClamp_TileMode, false, false); }
138b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GM* G100(void*) { return new GiantBitmapGM(SkShader::kRepeat_TileMode, false, false); }
139b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GM* G200(void*) { return new GiantBitmapGM(SkShader::kMirror_TileMode, false, false); }
140b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GM* G010(void*) { return new GiantBitmapGM(SkShader::kClamp_TileMode, true, false); }
141b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GM* G110(void*) { return new GiantBitmapGM(SkShader::kRepeat_TileMode, true, false); }
142b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GM* G210(void*) { return new GiantBitmapGM(SkShader::kMirror_TileMode, true, false); }
143b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.com
144b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GM* G001(void*) { return new GiantBitmapGM(SkShader::kClamp_TileMode, false, true); }
145b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GM* G101(void*) { return new GiantBitmapGM(SkShader::kRepeat_TileMode, false, true); }
146b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GM* G201(void*) { return new GiantBitmapGM(SkShader::kMirror_TileMode, false, true); }
147b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GM* G011(void*) { return new GiantBitmapGM(SkShader::kClamp_TileMode, true, true); }
148b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GM* G111(void*) { return new GiantBitmapGM(SkShader::kRepeat_TileMode, true, true); }
149b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GM* G211(void*) { return new GiantBitmapGM(SkShader::kMirror_TileMode, true, true); }
150b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.com
151b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GMRegistry reg000(G000);
152b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GMRegistry reg100(G100);
153b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GMRegistry reg200(G200);
154b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GMRegistry reg010(G010);
155b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GMRegistry reg110(G110);
156b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GMRegistry reg210(G210);
157b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.com
158b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GMRegistry reg001(G001);
159b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GMRegistry reg101(G101);
160b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GMRegistry reg201(G201);
161b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GMRegistry reg011(G011);
162b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GMRegistry reg111(G111);
163b0b462b93b2cc20727be6b849a1d2080d6bfd794reed@google.comstatic skiagm::GMRegistry reg211(G211);
164