SampleApp.cpp revision 09e3baaaf54a8a3c701cfc5ad24a8180464a4742
18a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com#include "SkCanvas.h"
28a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com#include "SkDevice.h"
3ac10a2d039c5d52eed66e27cbbc503ab523c1cd5reed@google.com#include "SkGpuCanvas.h"
48a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com#include "SkGraphics.h"
5b08eb2b3bce45411494fe00258e4c91248ccd15ereed@android.com#include "SkImageEncoder.h"
68a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com#include "SkPaint.h"
78a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com#include "SkPicture.h"
88a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com#include "SkStream.h"
94417740a480786ca65379ba5b398c500ba34ee18reed@android.com#include "SkTime.h"
108a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com#include "SkWindow.h"
118a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
128a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com#include "SampleCode.h"
13ac10a2d039c5d52eed66e27cbbc503ab523c1cd5reed@google.com#include "GrContext.h"
1452f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com#include "SkTouchGesture.h"
150f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo#include "SkTypeface.h"
16f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
17dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org#define USE_ARROWS_FOR_ZOOM true
18f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com//#define DEFAULT_TO_GPU
19f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
20e191b16fda2f5afea3a90653c1cd4f5a3c436e89reed@android.comextern SkView* create_overview(int, const SkViewFactory[]);
2134245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com
22cb34235f46b6259b612e72c416e850e26803250areed@android.com#define SK_SUPPORT_GL
238a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
248a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com#define ANIMATING_EVENTTYPE "nextSample"
258a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com#define ANIMATING_DELAY     750
268a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
272eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org#ifdef SK_DEBUG
282eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    #define FPS_REPEAT_COUNT    10
292eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org#else
302eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    #define FPS_REPEAT_COUNT    100
312eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org#endif
322eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org
33ac10a2d039c5d52eed66e27cbbc503ab523c1cd5reed@google.com#ifdef SK_SUPPORT_GL
34ac10a2d039c5d52eed66e27cbbc503ab523c1cd5reed@google.com    #include "GrGLConfig.h"
35ac10a2d039c5d52eed66e27cbbc503ab523c1cd5reed@google.com#endif
36ac10a2d039c5d52eed66e27cbbc503ab523c1cd5reed@google.com
372eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org///////////////
382eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.orgstatic const char view_inval_msg[] = "view-inval-msg";
392eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org
402eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.orgstatic void postInvalDelay(SkEventSinkID sinkID) {
412eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    SkEvent* evt = new SkEvent(view_inval_msg);
42f21833999d90ad9c8c584cff3238797b39cfc00breed@google.com    evt->post(sinkID, 1);
432eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org}
442eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org
452eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.orgstatic bool isInvalEvent(const SkEvent& evt) {
462eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    return evt.isType(view_inval_msg);
472eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org}
482eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org//////////////////
492eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org
508a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comSkViewRegister* SkViewRegister::gHead;
518a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comSkViewRegister::SkViewRegister(SkViewFactory fact) : fFact(fact) {
528a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    static bool gOnce;
538a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    if (!gOnce) {
548a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        gHead = NULL;
558a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        gOnce = true;
568a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    }
572e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
588a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    fChain = gHead;
598a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    gHead = this;
608a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
618a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
62f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com#if defined(SK_SUPPORT_GL)
63f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    #define SK_USE_SHADERS
648a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com#endif
658a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
6606c3b6bfd53c93d5ba49cf4d87b2c5c1bf33f072twiz@google.com#ifdef SK_BUILD_FOR_MAC
67f0b5f68807cfa18cce0647d275778147901945cdreed@google.com#include <CoreFoundation/CoreFoundation.h>
68f0b5f68807cfa18cce0647d275778147901945cdreed@google.com#include <CoreFoundation/CFURLAccess.h>
69f0b5f68807cfa18cce0647d275778147901945cdreed@google.com
70f0b5f68807cfa18cce0647d275778147901945cdreed@google.comstatic void testpdf() {
71f0b5f68807cfa18cce0647d275778147901945cdreed@google.com    CFStringRef path = CFStringCreateWithCString(NULL, "/test.pdf",
72f0b5f68807cfa18cce0647d275778147901945cdreed@google.com                                                 kCFStringEncodingUTF8);
73f0b5f68807cfa18cce0647d275778147901945cdreed@google.com    CFURLRef url = CFURLCreateWithFileSystemPath(NULL, path,
74f0b5f68807cfa18cce0647d275778147901945cdreed@google.com                                              kCFURLPOSIXPathStyle,
75f0b5f68807cfa18cce0647d275778147901945cdreed@google.com                                              false);
76f0b5f68807cfa18cce0647d275778147901945cdreed@google.com    CFRelease(path);
77f0b5f68807cfa18cce0647d275778147901945cdreed@google.com    CGRect box = CGRectMake(0, 0, 8*72, 10*72);
78f0b5f68807cfa18cce0647d275778147901945cdreed@google.com    CGContextRef cg = CGPDFContextCreateWithURL(url, &box, NULL);
79f0b5f68807cfa18cce0647d275778147901945cdreed@google.com    CFRelease(url);
80f0b5f68807cfa18cce0647d275778147901945cdreed@google.com
81f0b5f68807cfa18cce0647d275778147901945cdreed@google.com    CGContextBeginPage(cg, &box);
82f0b5f68807cfa18cce0647d275778147901945cdreed@google.com    CGRect r = CGRectMake(10, 10, 40 + 0.5, 50 + 0.5);
83f0b5f68807cfa18cce0647d275778147901945cdreed@google.com    CGContextFillEllipseInRect(cg, r);
84f0b5f68807cfa18cce0647d275778147901945cdreed@google.com    CGContextEndPage(cg);
85f0b5f68807cfa18cce0647d275778147901945cdreed@google.com    CGContextRelease(cg);
86f0b5f68807cfa18cce0647d275778147901945cdreed@google.com
87f0b5f68807cfa18cce0647d275778147901945cdreed@google.com    if (false) {
88f0b5f68807cfa18cce0647d275778147901945cdreed@google.com        SkBitmap bm;
89f0b5f68807cfa18cce0647d275778147901945cdreed@google.com        bm.setConfig(SkBitmap::kA8_Config, 64, 64);
90f0b5f68807cfa18cce0647d275778147901945cdreed@google.com        bm.allocPixels();
91f0b5f68807cfa18cce0647d275778147901945cdreed@google.com        bm.eraseColor(0);
92f0b5f68807cfa18cce0647d275778147901945cdreed@google.com
93f0b5f68807cfa18cce0647d275778147901945cdreed@google.com        SkCanvas canvas(bm);
94f0b5f68807cfa18cce0647d275778147901945cdreed@google.com
95f0b5f68807cfa18cce0647d275778147901945cdreed@google.com    }
96f0b5f68807cfa18cce0647d275778147901945cdreed@google.com}
97f0b5f68807cfa18cce0647d275778147901945cdreed@google.com#endif
98f0b5f68807cfa18cce0647d275778147901945cdreed@google.com
99f0b5f68807cfa18cce0647d275778147901945cdreed@google.com//////////////////////////////////////////////////////////////////////////////
100f0b5f68807cfa18cce0647d275778147901945cdreed@google.com
101569e0435af62bdb88a662fa0592f75673a17afd9reed@google.comenum FlipAxisEnum {
102569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    kFlipAxis_X = (1 << 0),
103569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    kFlipAxis_Y = (1 << 1)
104569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com};
105f0b5f68807cfa18cce0647d275778147901945cdreed@google.com
106569e0435af62bdb88a662fa0592f75673a17afd9reed@google.comenum SkTriState {
107569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    kFalse_SkTriState,
108569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    kTrue_SkTriState,
109569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    kUnknown_SkTriState,
110569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com};
111569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com
112569e0435af62bdb88a662fa0592f75673a17afd9reed@google.comstatic SkTriState cycle_tristate(SkTriState state) {
113569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    static const SkTriState gCycle[] = {
114569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com        /* kFalse_SkTriState   -> */  kUnknown_SkTriState,
115569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com        /* kTrue_SkTriState    -> */  kFalse_SkTriState,
116569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com        /* kUnknown_SkTriState -> */  kTrue_SkTriState,
117f0b5f68807cfa18cce0647d275778147901945cdreed@google.com    };
118569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    return gCycle[state];
119569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com}
120f0b5f68807cfa18cce0647d275778147901945cdreed@google.com
121569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com#include "SkDrawFilter.h"
122569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com
123569e0435af62bdb88a662fa0592f75673a17afd9reed@google.comclass FlagsDrawFilter : public SkDrawFilter {
124569e0435af62bdb88a662fa0592f75673a17afd9reed@google.compublic:
12509e3baaaf54a8a3c701cfc5ad24a8180464a4742reed@google.com    FlagsDrawFilter(SkTriState lcd, SkTriState aa, SkTriState filter,
12609e3baaaf54a8a3c701cfc5ad24a8180464a4742reed@google.com                    SkTriState hinting) :
12709e3baaaf54a8a3c701cfc5ad24a8180464a4742reed@google.com        fLCDState(lcd), fAAState(aa), fFilterState(filter), fHintingState(hinting) {}
128f0b5f68807cfa18cce0647d275778147901945cdreed@google.com
1293ce59dc4999de5d6c6913af662c8b0b8020a4ef7mike@reedtribe.org    virtual void filter(SkPaint* paint, Type t) {
130569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com        if (kText_Type == t && kUnknown_SkTriState != fLCDState) {
131569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com            paint->setLCDRenderText(kTrue_SkTriState == fLCDState);
132569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com        }
133569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com        if (kUnknown_SkTriState != fAAState) {
134569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com            paint->setAntiAlias(kTrue_SkTriState == fAAState);
135f0b5f68807cfa18cce0647d275778147901945cdreed@google.com        }
136176753aa6d695ebcb76c0f82265ad69dc41dc593reed@google.com        if (kUnknown_SkTriState != fFilterState) {
137176753aa6d695ebcb76c0f82265ad69dc41dc593reed@google.com            paint->setFilterBitmap(kTrue_SkTriState == fFilterState);
138176753aa6d695ebcb76c0f82265ad69dc41dc593reed@google.com        }
13909e3baaaf54a8a3c701cfc5ad24a8180464a4742reed@google.com        if (kUnknown_SkTriState != fHintingState) {
14009e3baaaf54a8a3c701cfc5ad24a8180464a4742reed@google.com            paint->setHinting(kTrue_SkTriState == fHintingState ?
14109e3baaaf54a8a3c701cfc5ad24a8180464a4742reed@google.com                              SkPaint::kNormal_Hinting :
14209e3baaaf54a8a3c701cfc5ad24a8180464a4742reed@google.com                              SkPaint::kSlight_Hinting);
14309e3baaaf54a8a3c701cfc5ad24a8180464a4742reed@google.com        }
144f0b5f68807cfa18cce0647d275778147901945cdreed@google.com    }
145f0b5f68807cfa18cce0647d275778147901945cdreed@google.com
146f0b5f68807cfa18cce0647d275778147901945cdreed@google.comprivate:
147569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    SkTriState  fLCDState;
148569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    SkTriState  fAAState;
149176753aa6d695ebcb76c0f82265ad69dc41dc593reed@google.com    SkTriState  fFilterState;
15009e3baaaf54a8a3c701cfc5ad24a8180464a4742reed@google.com    SkTriState  fHintingState;
151f0b5f68807cfa18cce0647d275778147901945cdreed@google.com};
152f0b5f68807cfa18cce0647d275778147901945cdreed@google.com
1538a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com//////////////////////////////////////////////////////////////////////////////
1548a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
155dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org#define MAX_ZOOM_LEVEL  8
156dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org#define MIN_ZOOM_LEVEL  -8
157dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org
158f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.comstatic const char gCharEvtName[] = "SampleCode_Char_Event";
159f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.comstatic const char gKeyEvtName[] = "SampleCode_Key_Event";
1608a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comstatic const char gTitleEvtName[] = "SampleCode_Title_Event";
1618a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comstatic const char gPrefSizeEvtName[] = "SampleCode_PrefSize_Event";
162f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.comstatic const char gFastTextEvtName[] = "SampleCode_FastText_Event";
163f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
164f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.combool SampleCode::CharQ(const SkEvent& evt, SkUnichar* outUni) {
165f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    if (evt.isType(gCharEvtName, sizeof(gCharEvtName) - 1)) {
166f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        if (outUni) {
167f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            *outUni = evt.getFast32();
168f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        }
169f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        return true;
170f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    }
171f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    return false;
172f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com}
173f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
174f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.combool SampleCode::KeyQ(const SkEvent& evt, SkKey* outKey) {
175f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    if (evt.isType(gKeyEvtName, sizeof(gKeyEvtName) - 1)) {
176f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        if (outKey) {
177f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            *outKey = (SkKey)evt.getFast32();
178f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        }
179f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        return true;
180f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    }
181f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    return false;
182f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com}
1838a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
1848a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.combool SampleCode::TitleQ(const SkEvent& evt) {
1858a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    return evt.isType(gTitleEvtName, sizeof(gTitleEvtName) - 1);
1868a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
1878a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
1888a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comvoid SampleCode::TitleR(SkEvent* evt, const char title[]) {
1898a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkASSERT(evt && TitleQ(*evt));
1908a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    evt->setString(gTitleEvtName, title);
1918a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
1928a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
1938a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.combool SampleCode::PrefSizeQ(const SkEvent& evt) {
1948a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    return evt.isType(gPrefSizeEvtName, sizeof(gPrefSizeEvtName) - 1);
1958a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
1968a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
1978a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comvoid SampleCode::PrefSizeR(SkEvent* evt, SkScalar width, SkScalar height) {
1988a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkASSERT(evt && PrefSizeQ(*evt));
1998a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkScalar size[2];
2008a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    size[0] = width;
2018a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    size[1] = height;
2028a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    evt->setScalars(gPrefSizeEvtName, 2, size);
2038a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
2048a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
205f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.combool SampleCode::FastTextQ(const SkEvent& evt) {
206f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    return evt.isType(gFastTextEvtName, sizeof(gFastTextEvtName) - 1);
207f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com}
208f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
209f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com///////////////////////////////////////////////////////////////////////////////
210f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
2114417740a480786ca65379ba5b398c500ba34ee18reed@android.comstatic SkMSec gAnimTime;
212f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.comstatic SkMSec gAnimTimePrev;
213f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
2144417740a480786ca65379ba5b398c500ba34ee18reed@android.comSkMSec SampleCode::GetAnimTime() { return gAnimTime; }
215f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.comSkMSec SampleCode::GetAnimTimeDelta() { return gAnimTime - gAnimTimePrev; }
216f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.comSkScalar SampleCode::GetAnimSecondsDelta() {
217f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    return SkDoubleToScalar(GetAnimTimeDelta() / 1000.0);
218f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com}
2194417740a480786ca65379ba5b398c500ba34ee18reed@android.com
2204417740a480786ca65379ba5b398c500ba34ee18reed@android.comSkScalar SampleCode::GetAnimScalar(SkScalar speed, SkScalar period) {
221f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    // since gAnimTime can be up to 32 bits, we can't convert it to a float
222f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    // or we'll lose the low bits. Hence we use doubles for the intermediate
223f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    // calculations
224f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    double seconds = (double)gAnimTime / 1000.0;
225f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    double value = SkScalarToDouble(speed) * seconds;
2264417740a480786ca65379ba5b398c500ba34ee18reed@android.com    if (period) {
227f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        value = ::fmod(value, SkScalarToDouble(period));
2284417740a480786ca65379ba5b398c500ba34ee18reed@android.com    }
229f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    return SkDoubleToScalar(value);
2304417740a480786ca65379ba5b398c500ba34ee18reed@android.com}
2314417740a480786ca65379ba5b398c500ba34ee18reed@android.com
2328a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com//////////////////////////////////////////////////////////////////////////////
2338a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
234f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.comstatic SkView* curr_view(SkWindow* wind) {
235f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    SkView::F2BIter iter(wind);
236f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    return iter.next();
237f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com}
238f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
2398a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comclass SampleWindow : public SkOSWindow {
24034245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com    SkTDArray<SkViewFactory> fSamples;
2418a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.compublic:
2422fbc7fa460c99bffa78b9afb9aaa4dc0db68e1babsalomon@google.com    SampleWindow(void* hwnd);
2432fbc7fa460c99bffa78b9afb9aaa4dc0db68e1babsalomon@google.com    virtual ~SampleWindow();
2448a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
245e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com    virtual void draw(SkCanvas* canvas);
246e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com
2478a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comprotected:
2488a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    virtual void onDraw(SkCanvas* canvas);
2492fbc7fa460c99bffa78b9afb9aaa4dc0db68e1babsalomon@google.com    virtual bool onHandleKey(SkKey key);
2508a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    virtual bool onHandleChar(SkUnichar);
2518a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    virtual void onSizeChange();
2522e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
2538a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    virtual SkCanvas* beforeChildren(SkCanvas*);
2548a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    virtual void afterChildren(SkCanvas*);
2556c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com    virtual void beforeChild(SkView* child, SkCanvas* canvas);
2566c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com    virtual void afterChild(SkView* child, SkCanvas* canvas);
2572e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
2582fbc7fa460c99bffa78b9afb9aaa4dc0db68e1babsalomon@google.com    virtual bool onEvent(const SkEvent& evt);
259f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    virtual bool onQuery(SkEvent* evt);
2608a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
261dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    virtual bool onDispatchClick(int x, int y, Click::State);
26252f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com    virtual bool onClick(Click* click);
26352f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com    virtual Click* onFindClickHandler(SkScalar x, SkScalar y);
26452f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com
2658a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com#if 0
2662fbc7fa460c99bffa78b9afb9aaa4dc0db68e1babsalomon@google.com    virtual bool handleChar(SkUnichar uni);
2672fbc7fa460c99bffa78b9afb9aaa4dc0db68e1babsalomon@google.com    virtual bool handleEvent(const SkEvent& evt);
2682fbc7fa460c99bffa78b9afb9aaa4dc0db68e1babsalomon@google.com    virtual bool handleKey(SkKey key);
2692fbc7fa460c99bffa78b9afb9aaa4dc0db68e1babsalomon@google.com    virtual bool handleKeyUp(SkKey key);
2708a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    virtual bool onHandleKeyUp(SkKey key);
2718a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com#endif
2722e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
2738a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comprivate:
27434245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com    int fCurrIndex;
2752e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
2768a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkPicture* fPicture;
277f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    SkGpuCanvas* fGpuCanvas;
2782e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com    GrContext* fGrContext;
2798a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkPath fClipPath;
2802e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
28152f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com    SkTouchGesture fGesture;
282dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    int      fZoomLevel;
283dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    SkScalar fZoomScale;
28452f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com
2858a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    enum CanvasType {
2868a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        kRaster_CanvasType,
2878a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        kPicture_CanvasType,
288f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        kGPU_CanvasType
2898a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    };
2908a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    CanvasType fCanvasType;
2918a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
2928a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    bool fUseClip;
293e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com    bool fNClip;
2948a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    bool fRepeatDrawing;
2958a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    bool fAnimating;
2966c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com    bool fRotate;
2976c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com    bool fScale;
298f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    bool fRequestGrabImage;
2990faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com    bool fUsePipe;
3002eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    bool fMeasureFPS;
3012eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    SkMSec fMeasureFPS_Time;
3022e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
3030f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    // The following are for the 'fatbits' drawing
3040f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    // Latest position of the mouse.
3050f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    int fMouseX, fMouseY;
3060f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    int fFatBitsScale;
3070f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    // Used by the text showing position and color values.
3080f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    SkTypeface* fTypeface;
3090f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    bool fShowZoomer;
3100f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo
311569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    SkTriState fLCDState;
312569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    SkTriState fAAState;
313176753aa6d695ebcb76c0f82265ad69dc41dc593reed@google.com    SkTriState fFilterState;
31409e3baaaf54a8a3c701cfc5ad24a8180464a4742reed@google.com    SkTriState fHintingState;
315569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    unsigned   fFlipAxis;
316f0b5f68807cfa18cce0647d275778147901945cdreed@google.com
3178a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    int fScrollTestX, fScrollTestY;
3182e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
3192e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com    bool make3DReady();
320dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    void changeZoomLevel(int delta);
3212e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
3228a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    void loadView(SkView*);
3238a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    void updateTitle();
3248a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    bool nextSample();
3258a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
3260f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    void toggleZoomer();
3270f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    bool zoomIn();
3280f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    bool zoomOut();
3290f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    void updatePointer(int x, int y);
3300f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo
3318a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    void postAnimatingEvent() {
3328a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        if (fAnimating) {
3338a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            SkEvent* evt = new SkEvent(ANIMATING_EVENTTYPE);
3348a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            evt->post(this->getSinkID(), ANIMATING_DELAY);
3358a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        }
3368a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    }
3372e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
3382e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
3398a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    static CanvasType cycle_canvastype(CanvasType);
3408a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
3418a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    typedef SkOSWindow INHERITED;
3428a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com};
3438a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
3440f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggobool SampleWindow::zoomIn()
3450f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo{
3460f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    // Arbitrarily decided
3470f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    if (fFatBitsScale == 25) return false;
3480f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    fFatBitsScale++;
3490f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    this->inval(NULL);
3500f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    return true;
3510f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo}
3520f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo
3530f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggobool SampleWindow::zoomOut()
3540f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo{
3550f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    if (fFatBitsScale == 1) return false;
3560f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    fFatBitsScale--;
3570f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    this->inval(NULL);
3580f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    return true;
3590f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo}
3600f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo
3610f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggovoid SampleWindow::toggleZoomer()
3620f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo{
3630f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    fShowZoomer = !fShowZoomer;
3640f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    this->inval(NULL);
3650f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo}
3660f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo
3670f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggovoid SampleWindow::updatePointer(int x, int y)
3680f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo{
3690f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    fMouseX = x;
3700f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    fMouseY = y;
3710f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    if (fShowZoomer) {
3720f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        this->inval(NULL);
3730f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    }
3740f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo}
3750f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo
3762e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.combool SampleWindow::make3DReady() {
3772e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
3782e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com#if defined(SK_SUPPORT_GL)
379498a623e2eacb709c23e5c5be6d4991ad83ab167bsalomon@google.com    if (attachGL()) {
38011f0b519766dabed4ce882f3ee7c07a68d3ccb52bsalomon@google.com        if (NULL != fGrContext) {
3818fe72477f204b1a45393e6a64caa84fd287b805bbsalomon@google.com        // various gr lifecycle tests
3828fe72477f204b1a45393e6a64caa84fd287b805bbsalomon@google.com        #if   0
3838fe72477f204b1a45393e6a64caa84fd287b805bbsalomon@google.com            fGrContext->freeGpuResources();
3848fe72477f204b1a45393e6a64caa84fd287b805bbsalomon@google.com        #elif 0
3858fe72477f204b1a45393e6a64caa84fd287b805bbsalomon@google.com            // this will leak resources.
3868fe72477f204b1a45393e6a64caa84fd287b805bbsalomon@google.com            fGrContext->contextLost();
3878fe72477f204b1a45393e6a64caa84fd287b805bbsalomon@google.com        #elif 0
38811f0b519766dabed4ce882f3ee7c07a68d3ccb52bsalomon@google.com            GrAssert(1 == fGrContext->refcnt());
38911f0b519766dabed4ce882f3ee7c07a68d3ccb52bsalomon@google.com            fGrContext->unref();
39011f0b519766dabed4ce882f3ee7c07a68d3ccb52bsalomon@google.com            fGrContext = NULL;
3918fe72477f204b1a45393e6a64caa84fd287b805bbsalomon@google.com        #endif
39211f0b519766dabed4ce882f3ee7c07a68d3ccb52bsalomon@google.com        }
3938fe72477f204b1a45393e6a64caa84fd287b805bbsalomon@google.com
394498a623e2eacb709c23e5c5be6d4991ad83ab167bsalomon@google.com        if (NULL == fGrContext) {
395498a623e2eacb709c23e5c5be6d4991ad83ab167bsalomon@google.com        #if defined(SK_USE_SHADERS)
39605ef510389950e1ae8dcba40e41e001db771b12dbsalomon@google.com            fGrContext = GrContext::Create(kOpenGL_Shaders_GrEngine, NULL);
397498a623e2eacb709c23e5c5be6d4991ad83ab167bsalomon@google.com        #else
39805ef510389950e1ae8dcba40e41e001db771b12dbsalomon@google.com            fGrContext = GrContext::Create(kOpenGL_Fixed_GrEngine, NULL);
399498a623e2eacb709c23e5c5be6d4991ad83ab167bsalomon@google.com        #endif
400569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com            SkDebugf("---- constructor\n");
401498a623e2eacb709c23e5c5be6d4991ad83ab167bsalomon@google.com        }
4022e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
403498a623e2eacb709c23e5c5be6d4991ad83ab167bsalomon@google.com        if (NULL != fGrContext) {
404498a623e2eacb709c23e5c5be6d4991ad83ab167bsalomon@google.com            return true;
405498a623e2eacb709c23e5c5be6d4991ad83ab167bsalomon@google.com        } else {
406498a623e2eacb709c23e5c5be6d4991ad83ab167bsalomon@google.com            detachGL();
407498a623e2eacb709c23e5c5be6d4991ad83ab167bsalomon@google.com        }
4082e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com    }
4092e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com#endif
4102e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com    SkDebugf("Failed to setup 3D");
4112e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com    return false;
4122e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com}
4132e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
4148a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comSampleWindow::CanvasType SampleWindow::cycle_canvastype(CanvasType ct) {
4158a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    static const CanvasType gCT[] = {
4168a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        kPicture_CanvasType,
417f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        kGPU_CanvasType,
4188a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        kRaster_CanvasType
4198a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    };
4208a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    return gCT[ct];
4218a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
4228a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
4238a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comSampleWindow::SampleWindow(void* hwnd) : INHERITED(hwnd) {
4248a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    fPicture = NULL;
425f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    fGpuCanvas = NULL;
4268a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
4272e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com    fGrContext = NULL;
4282e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
429f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com#ifdef DEFAULT_TO_GPU
430f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    fCanvasType = kGPU_CanvasType;
431f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com#else
4328a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    fCanvasType = kRaster_CanvasType;
433f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com#endif
4348a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    fUseClip = false;
435e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com    fNClip = false;
4368a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    fRepeatDrawing = false;
4378a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    fAnimating = false;
4386c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com    fRotate = false;
4396c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com    fScale = false;
440f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    fRequestGrabImage = false;
4410faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com    fUsePipe = false;
4422eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    fMeasureFPS = false;
443569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    fLCDState = kUnknown_SkTriState;
444569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    fAAState = kUnknown_SkTriState;
44566f22fd07aae8516bd1722ae32c360f9816d3cb2reed@google.com    fFilterState = kUnknown_SkTriState;
44609e3baaaf54a8a3c701cfc5ad24a8180464a4742reed@google.com    fHintingState = kUnknown_SkTriState;
447569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    fFlipAxis = 0;
4488a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    fScrollTestX = fScrollTestY = 0;
4498a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
4500f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    fMouseX = fMouseY = 0;
4513ce59dc4999de5d6c6913af662c8b0b8020a4ef7mike@reedtribe.org    fFatBitsScale = 8;
4520f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    fTypeface = SkTypeface::CreateFromTypeface(NULL, SkTypeface::kBold);
4530f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    fShowZoomer = false;
4540f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo
455dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    fZoomLevel = 0;
456dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    fZoomScale = SK_Scalar1;
457dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org
4582fbc7fa460c99bffa78b9afb9aaa4dc0db68e1babsalomon@google.com//    this->setConfig(SkBitmap::kRGB_565_Config);
4592fbc7fa460c99bffa78b9afb9aaa4dc0db68e1babsalomon@google.com    this->setConfig(SkBitmap::kARGB_8888_Config);
4602fbc7fa460c99bffa78b9afb9aaa4dc0db68e1babsalomon@google.com    this->setVisibleP(true);
461f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    this->setClipToBounds(false);
4628a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
46334245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com    {
46434245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com        const SkViewRegister* reg = SkViewRegister::Head();
46534245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com        while (reg) {
46634245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com            *fSamples.append() = reg->factory();
46734245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com            reg = reg->next();
46834245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com        }
46934245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com    }
47034245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com    fCurrIndex = 0;
471e0f13eeb8e527cfd2541063ba2dd89c7d31d71cereed@android.com    this->loadView(fSamples[fCurrIndex]());
472f0b5f68807cfa18cce0647d275778147901945cdreed@google.com
47306c3b6bfd53c93d5ba49cf4d87b2c5c1bf33f072twiz@google.com#ifdef SK_BUILD_FOR_MAC
474f0b5f68807cfa18cce0647d275778147901945cdreed@google.com    testpdf();
47506c3b6bfd53c93d5ba49cf4d87b2c5c1bf33f072twiz@google.com#endif
4768a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
4778a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
4788a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comSampleWindow::~SampleWindow() {
4798a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    delete fPicture;
480f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    delete fGpuCanvas;
4812e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com    if (NULL != fGrContext) {
4822e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com        fGrContext->unref();
4832e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com    }
4840f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    fTypeface->unref();
4858a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
4868a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
48755e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.comstatic SkBitmap capture_bitmap(SkCanvas* canvas) {
48855e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com    SkBitmap bm;
48955e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com    const SkBitmap& src = canvas->getDevice()->accessBitmap(false);
49055e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com    src.copyTo(&bm, src.config());
49155e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com    return bm;
49255e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com}
49355e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com
49455e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.comstatic bool bitmap_diff(SkCanvas* canvas, const SkBitmap& orig,
49555e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com                        SkBitmap* diff) {
49655e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com    const SkBitmap& src = canvas->getDevice()->accessBitmap(false);
4972e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
49855e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com    SkAutoLockPixels alp0(src);
49955e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com    SkAutoLockPixels alp1(orig);
50055e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com    for (int y = 0; y < src.height(); y++) {
50155e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com        const void* srcP = src.getAddr(0, y);
50255e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com        const void* origP = orig.getAddr(0, y);
50355e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com        size_t bytes = src.width() * src.bytesPerPixel();
50455e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com        if (memcmp(srcP, origP, bytes)) {
50555e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com            SkDebugf("---------- difference on line %d\n", y);
50655e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com            return true;
50755e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com        }
50855e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com    }
50955e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com    return false;
51055e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com}
51155e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com
5120f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggostatic void drawText(SkCanvas* canvas, SkString string, SkScalar left, SkScalar top, SkPaint& paint)
5130f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo{
5140f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    SkColor desiredColor = paint.getColor();
5150f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    paint.setColor(SK_ColorWHITE);
5160f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    const char* c_str = string.c_str();
5170f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    size_t size = string.size();
5180f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    SkRect bounds;
5190f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    paint.measureText(c_str, size, &bounds);
5200f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    bounds.offset(left, top);
5210f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    SkScalar inset = SkIntToScalar(-2);
5220f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    bounds.inset(inset, inset);
5230f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    canvas->drawRect(bounds, paint);
5240f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    if (desiredColor != SK_ColorBLACK) {
5250f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        paint.setColor(SK_ColorBLACK);
5260f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        canvas->drawText(c_str, size, left + SK_Scalar1, top + SK_Scalar1, paint);
5270f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    }
5280f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    paint.setColor(desiredColor);
5290f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    canvas->drawText(c_str, size, left, top, paint);
5300f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo}
5310f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo
5324417740a480786ca65379ba5b398c500ba34ee18reed@android.com#define XCLIP_N  8
5334417740a480786ca65379ba5b398c500ba34ee18reed@android.com#define YCLIP_N  8
534e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com
535e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.comvoid SampleWindow::draw(SkCanvas* canvas) {
5364417740a480786ca65379ba5b398c500ba34ee18reed@android.com    // update the animation time
537f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    gAnimTimePrev = gAnimTime;
5384417740a480786ca65379ba5b398c500ba34ee18reed@android.com    gAnimTime = SkTime::GetMSecs();
5394417740a480786ca65379ba5b398c500ba34ee18reed@android.com
540569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    SkScalar cx = SkScalarHalf(this->width());
541569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    SkScalar cy = SkScalarHalf(this->height());
542569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com
543dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    if (fZoomLevel) {
544dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org        SkMatrix m;
545dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org        SkPoint center;
546dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org        m = canvas->getTotalMatrix();//.invert(&m);
547dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org        m.mapXY(cx, cy, &center);
548dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org        cx = center.fX;
549dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org        cy = center.fY;
55011f0b519766dabed4ce882f3ee7c07a68d3ccb52bsalomon@google.com
551dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org        m.setTranslate(-cx, -cy);
552dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org        m.postScale(fZoomScale, fZoomScale);
553dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org        m.postTranslate(cx, cy);
55411f0b519766dabed4ce882f3ee7c07a68d3ccb52bsalomon@google.com
555dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org        canvas->concat(m);
556dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    }
55711f0b519766dabed4ce882f3ee7c07a68d3ccb52bsalomon@google.com
558569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    if (fFlipAxis) {
559569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com        SkMatrix m;
560569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com        m.setTranslate(cx, cy);
561569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com        if (fFlipAxis & kFlipAxis_X) {
562569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com            m.preScale(-SK_Scalar1, SK_Scalar1);
563569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com        }
564569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com        if (fFlipAxis & kFlipAxis_Y) {
565569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com            m.preScale(SK_Scalar1, -SK_Scalar1);
566569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com        }
567569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com        m.preTranslate(-cx, -cy);
568569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com        canvas->concat(m);
569569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    }
570569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com
57152f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com    // Apply any gesture matrix
57252f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com    if (true) {
57352f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com        const SkMatrix& localM = fGesture.localM();
57452f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com        if (localM.getType() & SkMatrix::kScale_Mask) {
57552f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com            canvas->setExternalMatrix(&localM);
57652f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com        }
57752f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com        canvas->concat(localM);
57852f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com        canvas->concat(fGesture.globalM());
57911f0b519766dabed4ce882f3ee7c07a68d3ccb52bsalomon@google.com
58052f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com        if (fGesture.isActive()) {
58152f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com            this->inval(NULL);
58252f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com        }
58352f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com    }
58411f0b519766dabed4ce882f3ee7c07a68d3ccb52bsalomon@google.com
585e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com    if (fNClip) {
58655e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com        this->INHERITED::draw(canvas);
58755e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com        SkBitmap orig = capture_bitmap(canvas);
588e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com
589e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com        const SkScalar w = this->width();
590e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com        const SkScalar h = this->height();
591e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com        const SkScalar cw = w / XCLIP_N;
592e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com        const SkScalar ch = h / YCLIP_N;
593e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com        for (int y = 0; y < YCLIP_N; y++) {
59455e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com            SkRect r;
59555e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com            r.fTop = y * ch;
59655e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com            r.fBottom = (y + 1) * ch;
59755e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com            if (y == YCLIP_N - 1) {
59855e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com                r.fBottom = h;
59955e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com            }
600e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com            for (int x = 0; x < XCLIP_N; x++) {
601e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com                SkAutoCanvasRestore acr(canvas, true);
60255e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com                r.fLeft = x * cw;
60355e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com                r.fRight = (x + 1) * cw;
60455e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com                if (x == XCLIP_N - 1) {
60555e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com                    r.fRight = w;
60655e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com                }
607e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com                canvas->clipRect(r);
608e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com                this->INHERITED::draw(canvas);
609e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com            }
610e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com        }
6112e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
61255e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com        SkBitmap diff;
61355e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com        if (bitmap_diff(canvas, orig, &diff)) {
61455e76b209c9249308a9ba3d75c2472dd55e9d298reed@android.com        }
615e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com    } else {
616e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com        this->INHERITED::draw(canvas);
617e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com    }
6180f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    if (fShowZoomer) {
6190f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        int count = canvas->save();
6200f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        canvas->resetMatrix();
6210f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        // Ensure the mouse position is on screen.
622261b8e2ca1cf22303ad95267f0bdc6e87e1bbe70reed@google.com        int width = SkScalarRound(this->width());
623261b8e2ca1cf22303ad95267f0bdc6e87e1bbe70reed@google.com        int height = SkScalarRound(this->height());
6240f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        if (fMouseX >= width) fMouseX = width - 1;
6250f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        else if (fMouseX < 0) fMouseX = 0;
6260f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        if (fMouseY >= height) fMouseY = height - 1;
6270f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        else if (fMouseY < 0) fMouseY = 0;
6280f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        SkBitmap bitmap = capture_bitmap(canvas);
6290f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        // Find the size of the zoomed in view, forced to be odd, so the examined pixel is in the middle.
6303ce59dc4999de5d6c6913af662c8b0b8020a4ef7mike@reedtribe.org        int zoomedWidth = (width >> 1) | 1;
6313ce59dc4999de5d6c6913af662c8b0b8020a4ef7mike@reedtribe.org        int zoomedHeight = (height >> 1) | 1;
6320f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        SkIRect src;
6330f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        src.set(0, 0, zoomedWidth / fFatBitsScale, zoomedHeight / fFatBitsScale);
6340f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        src.offset(fMouseX - (src.width()>>1), fMouseY - (src.height()>>1));
6350f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        SkRect dest;
6360f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        dest.set(0, 0, SkIntToScalar(zoomedWidth), SkIntToScalar(zoomedHeight));
6370f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        dest.offset(SkIntToScalar(width - zoomedWidth), SkIntToScalar(height - zoomedHeight));
6380f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        SkPaint paint;
6390f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        // Clear the background behind our zoomed in view
6400f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        paint.setColor(SK_ColorWHITE);
6410f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        canvas->drawRect(dest, paint);
6420f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        canvas->drawBitmapRect(bitmap, &src, dest);
6430f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        paint.setColor(SK_ColorBLACK);
6440f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        paint.setStyle(SkPaint::kStroke_Style);
6450f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        // Draw a border around the pixel in the middle
6460f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        SkRect originalPixel;
6470f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        originalPixel.set(SkIntToScalar(fMouseX), SkIntToScalar(fMouseY), SkIntToScalar(fMouseX + 1), SkIntToScalar(fMouseY + 1));
6480f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        SkMatrix matrix;
6490f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        SkRect scalarSrc;
6500f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        scalarSrc.set(src);
6510f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        SkColor color = bitmap.getColor(fMouseX, fMouseY);
6520f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        if (matrix.setRectToRect(scalarSrc, dest, SkMatrix::kFill_ScaleToFit)) {
6530f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo            SkRect pixel;
6540f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo            matrix.mapRect(&pixel, originalPixel);
6550f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo            // TODO Perhaps measure the values and make the outline white if it's "dark"
6560f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo            if (color == SK_ColorBLACK) {
6570f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo                paint.setColor(SK_ColorWHITE);
6580f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo            }
6590f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo            canvas->drawRect(pixel, paint);
6600f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        }
6610f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        paint.setColor(SK_ColorBLACK);
6620f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        // Draw a border around the destination rectangle
6630f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        canvas->drawRect(dest, paint);
6640f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        paint.setStyle(SkPaint::kStrokeAndFill_Style);
6650f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        // Identify the pixel and its color on screen
6660f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        paint.setTypeface(fTypeface);
6670f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        paint.setAntiAlias(true);
6680f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        SkScalar lineHeight = paint.getFontMetrics(NULL);
6690f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        SkString string;
6700f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        string.appendf("(%i, %i)", fMouseX, fMouseY);
6710f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        SkScalar left = dest.fLeft + SkIntToScalar(3);
6720f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        SkScalar i = SK_Scalar1;
6730f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        drawText(canvas, string, left, SkScalarMulAdd(lineHeight, i, dest.fTop), paint);
6740f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        // Alpha
6750f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        i += SK_Scalar1;
6760f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        string.reset();
6770f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        string.appendf("A: %X", SkColorGetA(color));
6780f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        drawText(canvas, string, left, SkScalarMulAdd(lineHeight, i, dest.fTop), paint);
6790f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        // Red
6800f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        i += SK_Scalar1;
6810f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        string.reset();
6820f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        string.appendf("R: %X", SkColorGetR(color));
6830f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        paint.setColor(SK_ColorRED);
6840f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        drawText(canvas, string, left, SkScalarMulAdd(lineHeight, i, dest.fTop), paint);
6850f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        // Green
6860f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        i += SK_Scalar1;
6870f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        string.reset();
6880f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        string.appendf("G: %X", SkColorGetG(color));
6890f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        paint.setColor(SK_ColorGREEN);
6900f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        drawText(canvas, string, left, SkScalarMulAdd(lineHeight, i, dest.fTop), paint);
6910f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        // Blue
6920f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        i += SK_Scalar1;
6930f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        string.reset();
6940f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        string.appendf("B: %X", SkColorGetB(color));
6950f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        paint.setColor(SK_ColorBLUE);
6960f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        drawText(canvas, string, left, SkScalarMulAdd(lineHeight, i, dest.fTop), paint);
6970f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        canvas->restoreToCount(count);
6980f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    }
699e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com}
700e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com
7018a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comvoid SampleWindow::onDraw(SkCanvas* canvas) {
7028a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    if (fRepeatDrawing) {
7038a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        this->inval(NULL);
7048a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    }
7058a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
7068a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
7078a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com#include "SkColorPriv.h"
7088a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
7098a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comstatic void reverseRedAndBlue(const SkBitmap& bm) {
7108a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkASSERT(bm.config() == SkBitmap::kARGB_8888_Config);
7118a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    uint8_t* p = (uint8_t*)bm.getPixels();
7128a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    uint8_t* stop = p + bm.getSize();
7138a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    while (p < stop) {
7148a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        // swap red/blue (to go from ARGB(int) to RGBA(memory) and premultiply
7158a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        unsigned scale = SkAlpha255To256(p[3]);
7168a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        unsigned r = p[2];
7178a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        unsigned b = p[0];
7188a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        p[0] = SkAlphaMul(r, scale);
7198a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        p[1] = SkAlphaMul(p[1], scale);
7208a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        p[2] = SkAlphaMul(b, scale);
7218a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        p += 4;
7228a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    }
7238a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
7248a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
7258a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comSkCanvas* SampleWindow::beforeChildren(SkCanvas* canvas) {
726f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    if (kGPU_CanvasType != fCanvasType) {
7276efdc47afc8bb24603fc0d15146ada609b728f2freed@android.com#ifdef SK_SUPPORT_GL
728f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        detachGL();
7292e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com#endif
730f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    }
7312e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
7328a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    switch (fCanvasType) {
7338a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        case kRaster_CanvasType:
7348a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            canvas = this->INHERITED::beforeChildren(canvas);
7358a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            break;
7368a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        case kPicture_CanvasType:
7378a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            fPicture = new SkPicture;
7388a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            canvas = fPicture->beginRecording(9999, 9999);
7398a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            break;
740ac10a2d039c5d52eed66e27cbbc503ab523c1cd5reed@google.com        case kGPU_CanvasType: {
74164e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com            if (make3DReady()) {
742f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com                SkDevice* device = canvas->getDevice();
7432e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com                const SkBitmap& bitmap = device->accessBitmap(true);
7442e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
7455782d712ffc31557d0cb12d5a220cebb783f6895bsalomon@google.com                GrRenderTarget* renderTarget;
7465782d712ffc31557d0cb12d5a220cebb783f6895bsalomon@google.com                renderTarget = fGrContext->createRenderTargetFrom3DApiState();
7475782d712ffc31557d0cb12d5a220cebb783f6895bsalomon@google.com                fGpuCanvas = new SkGpuCanvas(fGrContext, renderTarget);
7485782d712ffc31557d0cb12d5a220cebb783f6895bsalomon@google.com                renderTarget->unref();
7495782d712ffc31557d0cb12d5a220cebb783f6895bsalomon@google.com
7502fbc7fa460c99bffa78b9afb9aaa4dc0db68e1babsalomon@google.com                device = fGpuCanvas->createDevice(SkBitmap::kARGB_8888_Config,
7512fbc7fa460c99bffa78b9afb9aaa4dc0db68e1babsalomon@google.com                                                  bitmap.width(), bitmap.height(),
7522fbc7fa460c99bffa78b9afb9aaa4dc0db68e1babsalomon@google.com                                                  false, false);
753ac10a2d039c5d52eed66e27cbbc503ab523c1cd5reed@google.com                fGpuCanvas->setDevice(device)->unref();
75411f0b519766dabed4ce882f3ee7c07a68d3ccb52bsalomon@google.com
755dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org                fGpuCanvas->concat(canvas->getTotalMatrix());
756f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com                canvas = fGpuCanvas;
7572e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
758f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            } else {
759f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com                canvas = this->INHERITED::beforeChildren(canvas);
760f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            }
7618a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            break;
762ac10a2d039c5d52eed66e27cbbc503ab523c1cd5reed@google.com        }
7638a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    }
7648a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
7658a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    if (fUseClip) {
7668a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        canvas->drawColor(0xFFFF88FF);
7678a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        canvas->clipPath(fClipPath);
7688a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    }
7698a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
7708a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    return canvas;
7718a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
7728a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
7738a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comstatic void paint_rgn(const SkBitmap& bm, const SkIRect& r,
7748a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                      const SkRegion& rgn) {
7758a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkCanvas    canvas(bm);
7768a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkRegion    inval(rgn);
7778a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
7788a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    inval.translate(r.fLeft, r.fTop);
7798a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    canvas.clipRegion(inval);
7808a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    canvas.drawColor(0xFFFF8080);
7818a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
7828a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
7838a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comvoid SampleWindow::afterChildren(SkCanvas* orig) {
784f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    if (fRequestGrabImage) {
785f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        fRequestGrabImage = false;
7862e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
787f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        SkCanvas* canvas = fGpuCanvas ? fGpuCanvas : orig;
788f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        SkDevice* device = canvas->getDevice();
789669fdc4ed8ed461a141cb97d0afdd9ef72a82be1bsalomon@google.com        SkBitmap bmp;
790669fdc4ed8ed461a141cb97d0afdd9ef72a82be1bsalomon@google.com        if (device->accessBitmap(false).copyTo(&bmp, SkBitmap::kARGB_8888_Config)) {
791f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            static int gSampleGrabCounter;
792f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            SkString name;
793f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            name.printf("sample_grab_%d", gSampleGrabCounter++);
794669fdc4ed8ed461a141cb97d0afdd9ef72a82be1bsalomon@google.com            SkImageEncoder::EncodeFile(name.c_str(), bmp,
795f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com                                       SkImageEncoder::kPNG_Type, 100);
796f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        }
797f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    }
798f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
7998a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    switch (fCanvasType) {
8008a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        case kRaster_CanvasType:
8018a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            break;
8028a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        case kPicture_CanvasType:
803aefd2bc75738963b9b6579897be32bfbc8fb00afreed@android.com            if (true) {
8048a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                SkPicture* pict = new SkPicture(*fPicture);
8058a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                fPicture->unref();
8068a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                orig->drawPicture(*pict);
8078a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                pict->unref();
808aefd2bc75738963b9b6579897be32bfbc8fb00afreed@android.com            } else if (true) {
8098a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                SkDynamicMemoryWStream ostream;
8108a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                fPicture->serialize(&ostream);
8118a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                fPicture->unref();
8122e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
8138a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                SkMemoryStream istream(ostream.getStream(), ostream.getOffset());
8148a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                SkPicture pict(&istream);
8158a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                orig->drawPicture(pict);
8168a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            } else {
8178a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                fPicture->draw(orig);
8188a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                fPicture->unref();
8198a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            }
8208a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            fPicture = NULL;
8218a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            break;
8226efdc47afc8bb24603fc0d15146ada609b728f2freed@android.com#ifdef SK_SUPPORT_GL
823f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        case kGPU_CanvasType:
824f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            delete fGpuCanvas;
825f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            fGpuCanvas = NULL;
826f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            presentGL();
827f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            break;
8286efdc47afc8bb24603fc0d15146ada609b728f2freed@android.com#endif
8298a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    }
8302e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
83117d7aec8967f7e2f6bb420c6647be11285fac2f1reed@google.com    // Do this after presentGL and other finishing, rather than in afterChild
83217d7aec8967f7e2f6bb420c6647be11285fac2f1reed@google.com    if (fMeasureFPS && fMeasureFPS_Time) {
83317d7aec8967f7e2f6bb420c6647be11285fac2f1reed@google.com        fMeasureFPS_Time = SkTime::GetMSecs() - fMeasureFPS_Time;
83417d7aec8967f7e2f6bb420c6647be11285fac2f1reed@google.com        this->updateTitle();
83517d7aec8967f7e2f6bb420c6647be11285fac2f1reed@google.com        postInvalDelay(this->getSinkID());
83617d7aec8967f7e2f6bb420c6647be11285fac2f1reed@google.com    }
83717d7aec8967f7e2f6bb420c6647be11285fac2f1reed@google.com
83817d7aec8967f7e2f6bb420c6647be11285fac2f1reed@google.com    //    if ((fScrollTestX | fScrollTestY) != 0)
839f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    if (false) {
8408a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        const SkBitmap& bm = orig->getDevice()->accessBitmap(true);
8418a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        int dx = fScrollTestX * 7;
8428a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        int dy = fScrollTestY * 7;
8438a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        SkIRect r;
8448a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        SkRegion inval;
8452e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
8468a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        r.set(50, 50, 50+100, 50+100);
8478a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        bm.scrollRect(&r, dx, dy, &inval);
8488a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        paint_rgn(bm, r, inval);
8492eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    }
8508a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
8518a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
8526c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.comvoid SampleWindow::beforeChild(SkView* child, SkCanvas* canvas) {
8536c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com    if (fScale) {
8546c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com        SkScalar scale = SK_Scalar1 * 7 / 10;
8556c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com        SkScalar cx = this->width() / 2;
8566c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com        SkScalar cy = this->height() / 2;
8576c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com        canvas->translate(cx, cy);
8586c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com        canvas->scale(scale, scale);
8596c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com        canvas->translate(-cx, -cy);
8606c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com    }
8616c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com    if (fRotate) {
8626c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com        SkScalar cx = this->width() / 2;
8636c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com        SkScalar cy = this->height() / 2;
8646c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com        canvas->translate(cx, cy);
8656c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com        canvas->rotate(SkIntToScalar(30));
8666c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com        canvas->translate(-cx, -cy);
8676c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com    }
868f0b5f68807cfa18cce0647d275778147901945cdreed@google.com
86909e3baaaf54a8a3c701cfc5ad24a8180464a4742reed@google.com    canvas->setDrawFilter(new FlagsDrawFilter(fLCDState, fAAState,
87009e3baaaf54a8a3c701cfc5ad24a8180464a4742reed@google.com                                       fFilterState, fHintingState))->unref();
8712eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org
8722eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    if (fMeasureFPS) {
873f21833999d90ad9c8c584cff3238797b39cfc00breed@google.com        fMeasureFPS_Time = 0;   // 0 means the child is not aware of repeat-draw
874f21833999d90ad9c8c584cff3238797b39cfc00breed@google.com        if (SampleView::SetRepeatDraw(child, FPS_REPEAT_COUNT)) {
875f21833999d90ad9c8c584cff3238797b39cfc00breed@google.com            fMeasureFPS_Time = SkTime::GetMSecs();
876f21833999d90ad9c8c584cff3238797b39cfc00breed@google.com        }
877f21833999d90ad9c8c584cff3238797b39cfc00breed@google.com    } else {
878f21833999d90ad9c8c584cff3238797b39cfc00breed@google.com        (void)SampleView::SetRepeatDraw(child, 1);
8792eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    }
8800faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com    (void)SampleView::SetUsePipe(child, fUsePipe);
8816c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com}
8826c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com
8836c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.comvoid SampleWindow::afterChild(SkView* child, SkCanvas* canvas) {
884f0b5f68807cfa18cce0647d275778147901945cdreed@google.com    canvas->setDrawFilter(NULL);
8856c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com}
8866c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com
8878a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comstatic SkBitmap::Config gConfigCycle[] = {
8888a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkBitmap::kNo_Config,           // none -> none
8898a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkBitmap::kNo_Config,           // a1 -> none
8908a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkBitmap::kNo_Config,           // a8 -> none
8918a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkBitmap::kNo_Config,           // index8 -> none
8928a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkBitmap::kARGB_4444_Config,    // 565 -> 4444
8938a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkBitmap::kARGB_8888_Config,    // 4444 -> 8888
8948a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkBitmap::kRGB_565_Config       // 8888 -> 565
8958a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com};
8968a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
8978a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comstatic SkBitmap::Config cycle_configs(SkBitmap::Config c) {
8988a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    return gConfigCycle[c];
8998a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
9008a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
901dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.orgvoid SampleWindow::changeZoomLevel(int delta) {
902dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    fZoomLevel += delta;
903dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    if (fZoomLevel > 0) {
904dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org        fZoomLevel = SkMin32(fZoomLevel, MAX_ZOOM_LEVEL);
905dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org        fZoomScale = SkIntToScalar(fZoomLevel + 1);
906dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    } else if (fZoomLevel < 0) {
907dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org        fZoomLevel = SkMax32(fZoomLevel, MIN_ZOOM_LEVEL);
908dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org        fZoomScale = SK_Scalar1 / (1 - fZoomLevel);
909dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    } else {
910dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org        fZoomScale = SK_Scalar1;
911dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    }
912dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org
913dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    this->inval(NULL);
914dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org}
915dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org
9168a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.combool SampleWindow::nextSample() {
91734245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com    fCurrIndex = (fCurrIndex + 1) % fSamples.count();
91834245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com    this->loadView(fSamples[fCurrIndex]());
91934245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com    return true;
9208a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
9218a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
9228a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.combool SampleWindow::onEvent(const SkEvent& evt) {
9238a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    if (evt.isType(ANIMATING_EVENTTYPE)) {
9248a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        if (fAnimating) {
9258a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            this->nextSample();
9268a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            this->postAnimatingEvent();
9278a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        }
9288a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        return true;
9298a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    }
93034245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com    if (evt.isType("set-curr-index")) {
93134245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com        fCurrIndex = evt.getFast32() % fSamples.count();
93234245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com        this->loadView(fSamples[fCurrIndex]());
93334245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com        return true;
93434245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com    }
9352eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    if (isInvalEvent(evt)) {
9362eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org        this->inval(NULL);
9372eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org        return true;
9382eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    }
9398a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    return this->INHERITED::onEvent(evt);
9408a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
9418a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
942f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.combool SampleWindow::onQuery(SkEvent* query) {
943f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    if (query->isType("get-slide-count")) {
944f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        query->setFast32(fSamples.count());
945f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        return true;
946f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    }
947f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    if (query->isType("get-slide-title")) {
948f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        SkView* view = fSamples[query->getFast32()]();
949f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        SkEvent evt(gTitleEvtName);
950f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        if (view->doQuery(&evt)) {
951f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            query->setString("title", evt.findString(gTitleEvtName));
952f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        }
953f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        SkSafeUnref(view);
954f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        return true;
955f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    }
956f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    if (query->isType("use-fast-text")) {
957f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        SkEvent evt(gFastTextEvtName);
958f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        return curr_view(this)->doQuery(&evt);
959f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    }
960f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    return this->INHERITED::onQuery(query);
961f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com}
962f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
9630ae6b245f2b79bc04f0801b08fcf05abcf98fd6creed@android.comstatic void cleanup_for_filename(SkString* name) {
9640ae6b245f2b79bc04f0801b08fcf05abcf98fd6creed@android.com    char* str = name->writable_str();
965e191b16fda2f5afea3a90653c1cd4f5a3c436e89reed@android.com    for (size_t i = 0; i < name->size(); i++) {
9660ae6b245f2b79bc04f0801b08fcf05abcf98fd6creed@android.com        switch (str[i]) {
9670ae6b245f2b79bc04f0801b08fcf05abcf98fd6creed@android.com            case ':': str[i] = '-'; break;
9680ae6b245f2b79bc04f0801b08fcf05abcf98fd6creed@android.com            case '/': str[i] = '-'; break;
9690ae6b245f2b79bc04f0801b08fcf05abcf98fd6creed@android.com            case ' ': str[i] = '_'; break;
9700ae6b245f2b79bc04f0801b08fcf05abcf98fd6creed@android.com            default: break;
9710ae6b245f2b79bc04f0801b08fcf05abcf98fd6creed@android.com        }
9720ae6b245f2b79bc04f0801b08fcf05abcf98fd6creed@android.com    }
9730ae6b245f2b79bc04f0801b08fcf05abcf98fd6creed@android.com}
9748a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
9758a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.combool SampleWindow::onHandleChar(SkUnichar uni) {
976f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    {
977f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        SkView* view = curr_view(this);
978f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        if (view) {
979f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            SkEvent evt(gCharEvtName);
980f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            evt.setFast32(uni);
981f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            if (view->doQuery(&evt)) {
982f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com                return true;
983f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            }
984f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        }
985f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    }
9862e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
9878a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    int dx = 0xFF;
9888a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    int dy = 0xFF;
9898a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
9908a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    switch (uni) {
9918a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        case '5': dx =  0; dy =  0; break;
9928a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        case '8': dx =  0; dy = -1; break;
9938a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        case '6': dx =  1; dy =  0; break;
9948a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        case '2': dx =  0; dy =  1; break;
9958a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        case '4': dx = -1; dy =  0; break;
9968a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        case '7': dx = -1; dy = -1; break;
9978a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        case '9': dx =  1; dy = -1; break;
9988a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        case '3': dx =  1; dy =  1; break;
9998a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        case '1': dx = -1; dy =  1; break;
10002e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
10018a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        default:
10028a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            break;
10038a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    }
10042e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
10058a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    if (0xFF != dx && 0xFF != dy) {
10068a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        if ((dx | dy) == 0) {
10078a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            fScrollTestX = fScrollTestY = 0;
10088a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        } else {
10098a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            fScrollTestX += dx;
10108a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            fScrollTestY += dy;
10118a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        }
10128a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        this->inval(NULL);
10138a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        return true;
10148a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    }
10152e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
10160ae6b245f2b79bc04f0801b08fcf05abcf98fd6creed@android.com    switch (uni) {
10170ae6b245f2b79bc04f0801b08fcf05abcf98fd6creed@android.com        case 'a':
10180ae6b245f2b79bc04f0801b08fcf05abcf98fd6creed@android.com            fAnimating = !fAnimating;
10190ae6b245f2b79bc04f0801b08fcf05abcf98fd6creed@android.com            this->postAnimatingEvent();
10200ae6b245f2b79bc04f0801b08fcf05abcf98fd6creed@android.com            this->updateTitle();
10210ae6b245f2b79bc04f0801b08fcf05abcf98fd6creed@android.com            return true;
10222eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org        case 'b':
10232eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org            fAAState = cycle_tristate(fAAState);
10246c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com            this->updateTitle();
10256c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com            this->inval(NULL);
10262eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org            break;
1027fb56a9ee2d64e11aae6d225cb905e95e4a0ee6e5reed@google.com        case 'c':
1028fb56a9ee2d64e11aae6d225cb905e95e4a0ee6e5reed@google.com            fUseClip = !fUseClip;
1029fb56a9ee2d64e11aae6d225cb905e95e4a0ee6e5reed@google.com            this->inval(NULL);
1030fb56a9ee2d64e11aae6d225cb905e95e4a0ee6e5reed@google.com            this->updateTitle();
1031fb56a9ee2d64e11aae6d225cb905e95e4a0ee6e5reed@google.com            return true;
1032f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        case 'd':
1033f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            SkGraphics::SetFontCacheUsed(0);
1034f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            return true;
10352eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org        case 'f':
10362eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org            fMeasureFPS = !fMeasureFPS;
10372eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org            this->inval(NULL);
10382eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org            break;
1039f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        case 'g':
1040f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            fRequestGrabImage = true;
1041f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            this->inval(NULL);
1042f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            break;
104309e3baaaf54a8a3c701cfc5ad24a8180464a4742reed@google.com        case 'h':
104409e3baaaf54a8a3c701cfc5ad24a8180464a4742reed@google.com            fHintingState = cycle_tristate(fHintingState);
104509e3baaaf54a8a3c701cfc5ad24a8180464a4742reed@google.com            this->updateTitle();
104609e3baaaf54a8a3c701cfc5ad24a8180464a4742reed@google.com            this->inval(NULL);
104709e3baaaf54a8a3c701cfc5ad24a8180464a4742reed@google.com            break;
10482eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org        case 'i':
10492eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org            this->zoomIn();
10502eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org            break;
1051f0b5f68807cfa18cce0647d275778147901945cdreed@google.com        case 'l':
1052569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com            fLCDState = cycle_tristate(fLCDState);
1053569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com            this->updateTitle();
1054569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com            this->inval(NULL);
1055569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com            break;
1056176753aa6d695ebcb76c0f82265ad69dc41dc593reed@google.com        case 'n':
1057176753aa6d695ebcb76c0f82265ad69dc41dc593reed@google.com            fFilterState = cycle_tristate(fFilterState);
1058176753aa6d695ebcb76c0f82265ad69dc41dc593reed@google.com            this->updateTitle();
1059176753aa6d695ebcb76c0f82265ad69dc41dc593reed@google.com            this->inval(NULL);
1060176753aa6d695ebcb76c0f82265ad69dc41dc593reed@google.com            break;
106108526c07f4f530e56b70d4b22f5a4af35d9ebccascroggo        case 'o':
106208526c07f4f530e56b70d4b22f5a4af35d9ebccascroggo            this->zoomOut();
106308526c07f4f530e56b70d4b22f5a4af35d9ebccascroggo            break;
10640faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com        case 'p':
10650faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com            fUsePipe = !fUsePipe;
1066a6ff4dc22d5006dc588769aa20c8b0bb4fde6d43reed@google.com            this->updateTitle();
10670faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com            this->inval(NULL);
10680faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com            break;
10692eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org        case 'r':
10702eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org            fRotate = !fRotate;
10712eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org            this->inval(NULL);
10722eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org            this->updateTitle();
10732eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org            return true;
10742eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org        case 's':
10752eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org            fScale = !fScale;
10762eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org            this->inval(NULL);
10772eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org            this->updateTitle();
10782eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org            return true;
1079569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com        case 'x':
1080569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com            fFlipAxis ^= kFlipAxis_X;
1081569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com            this->updateTitle();
1082569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com            this->inval(NULL);
1083569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com            break;
1084569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com        case 'y':
1085569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com            fFlipAxis ^= kFlipAxis_Y;
1086569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com            this->updateTitle();
1087569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com            this->inval(NULL);
1088569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com            break;
108908526c07f4f530e56b70d4b22f5a4af35d9ebccascroggo        case 'z':
109008526c07f4f530e56b70d4b22f5a4af35d9ebccascroggo            this->toggleZoomer();
109108526c07f4f530e56b70d4b22f5a4af35d9ebccascroggo            break;
10920ae6b245f2b79bc04f0801b08fcf05abcf98fd6creed@android.com        default:
10930ae6b245f2b79bc04f0801b08fcf05abcf98fd6creed@android.com            break;
10948a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    }
10952e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
10968a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    return this->INHERITED::onHandleChar(uni);
10978a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
10988a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
10998a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com#include "SkDumpCanvas.h"
11008a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
11018a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.combool SampleWindow::onHandleKey(SkKey key) {
1102f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    {
1103f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        SkView* view = curr_view(this);
1104f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        if (view) {
1105f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            SkEvent evt(gKeyEvtName);
1106f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            evt.setFast32(key);
1107f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            if (view->doQuery(&evt)) {
1108f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com                return true;
1109f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            }
1110f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        }
1111f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    }
1112f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
11138a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    switch (key) {
11148a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        case kRight_SkKey:
11158a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            if (this->nextSample()) {
11168a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                return true;
11178a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            }
11188a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            break;
11198a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        case kLeft_SkKey:
11208a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            fCanvasType = cycle_canvastype(fCanvasType);
11218a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            this->updateTitle();
11228a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            this->inval(NULL);
11238a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            return true;
11248a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        case kUp_SkKey:
1125dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org            if (USE_ARROWS_FOR_ZOOM) {
1126dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org                this->changeZoomLevel(1);
1127dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org            } else {
1128dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org                fNClip = !fNClip;
1129dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org                this->inval(NULL);
1130dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org            }
11318a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            this->updateTitle();
11328a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            return true;
11338a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        case kDown_SkKey:
1134dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org            if (USE_ARROWS_FOR_ZOOM) {
1135dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org                this->changeZoomLevel(-1);
1136dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org            } else {
1137dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org                this->setConfig(cycle_configs(this->getBitmap().config()));
1138dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org            }
11398a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            this->updateTitle();
11408a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            return true;
11418a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        case kOK_SkKey:
1142f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            if (false) {
11438a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                SkDebugfDumper dumper;
11448a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                SkDumpCanvas dc(&dumper);
11458a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                this->draw(&dc);
11468a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            } else {
11478a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                fRepeatDrawing = !fRepeatDrawing;
11488a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                if (fRepeatDrawing) {
11498a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                    this->inval(NULL);
11508a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                }
11518a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            }
11528a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            return true;
115334245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com        case kBack_SkKey:
115434245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com            this->loadView(NULL);
115534245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com            return true;
11568a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        default:
11578a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            break;
11588a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    }
11598a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    return this->INHERITED::onHandleKey(key);
11608a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
11618a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
116252f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com///////////////////////////////////////////////////////////////////////////////
116352f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com
116452f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.comstatic const char gGestureClickType[] = "GestureClickType";
116552f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com
1166dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.orgbool SampleWindow::onDispatchClick(int x, int y, Click::State state) {
11670f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    if (Click::kMoved_State == state) {
11680f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo        updatePointer(x, y);
11690f185c2709f638c0f4d452cb38b434cadfd15ab9Scroggo    }
1170dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    int w = SkScalarRound(this->width());
1171dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    int h = SkScalarRound(this->height());
1172dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org
1173dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    // check for the resize-box
1174dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    if (w - x < 16 && h - y < 16) {
1175dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org        return false;   // let the OS handle the click
1176dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    } else {
1177dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org        return this->INHERITED::onDispatchClick(x, y, state);
1178dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    }
1179dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org}
1180dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org
118152f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.comclass GestureClick : public SkView::Click {
118252f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.compublic:
118352f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com    GestureClick(SkView* target) : SkView::Click(target) {
118452f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com        this->setType(gGestureClickType);
118552f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com    }
118652f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com
118752f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com    static bool IsGesture(Click* click) {
118852f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com        return click->isType(gGestureClickType);
118952f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com    }
119052f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com};
119152f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com
119252f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.comSkView::Click* SampleWindow::onFindClickHandler(SkScalar x, SkScalar y) {
119352f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com    return new GestureClick(this);
119452f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com}
119552f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com
119652f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.combool SampleWindow::onClick(Click* click) {
119752f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com    if (GestureClick::IsGesture(click)) {
119852f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com        float x = SkScalarToFloat(click->fCurr.fX);
119952f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com        float y = SkScalarToFloat(click->fCurr.fY);
120052f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com        switch (click->fState) {
120152f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com            case SkView::Click::kDown_State:
120252f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com                fGesture.touchBegin(click, x, y);
120352f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com                break;
120452f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com            case SkView::Click::kMoved_State:
120552f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com                fGesture.touchMoved(click, x, y);
120652f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com                this->inval(NULL);
120752f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com                break;
120852f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com            case SkView::Click::kUp_State:
120952f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com                fGesture.touchEnd(click);
121052f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com                this->inval(NULL);
121152f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com                break;
121252f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com        }
121352f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com        return true;
121452f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com    }
121552f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com    return false;
121652f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com}
121752f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com
121852f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com///////////////////////////////////////////////////////////////////////////////
121952f57e1d11a00bdc5efb96709446546cdbc1ff9dreed@google.com
12208a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comvoid SampleWindow::loadView(SkView* view) {
12218a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkView::F2BIter iter(this);
12228a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkView* prev = iter.next();
12238a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    if (prev) {
12248a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        prev->detachFromParent();
12258a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    }
12262e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
122734245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com    if (NULL == view) {
122834245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com        view = create_overview(fSamples.count(), fSamples.begin());
122934245c7871f6339de8cc2be8fb1090ca3cba54efreed@android.com    }
12308a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    view->setVisibleP(true);
1231f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    view->setClipToBounds(false);
12328a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    this->attachChildToFront(view)->unref();
12338a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    view->setSize(this->width(), this->height());
12348a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
12358a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    this->updateTitle();
12368a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
12378a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
12388a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comstatic const char* gConfigNames[] = {
12398a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    "unknown config",
12408a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    "A1",
12418a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    "A8",
12428a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    "Index8",
12438a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    "565",
12448a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    "4444",
12458a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    "8888"
12468a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com};
12478a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
12488a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comstatic const char* configToString(SkBitmap::Config c) {
12498a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    return gConfigNames[c];
12508a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
12518a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
12528a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comstatic const char* gCanvasTypePrefix[] = {
12538a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    "raster: ",
12548a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    "picture: ",
12558a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    "opengl: "
12568a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com};
12578a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
1258569e0435af62bdb88a662fa0592f75673a17afd9reed@google.comstatic const char* trystate_str(SkTriState state,
1259569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com                                const char trueStr[], const char falseStr[]) {
1260569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    if (kTrue_SkTriState == state) {
1261569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com        return trueStr;
1262569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    } else if (kFalse_SkTriState == state) {
1263569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com        return falseStr;
1264569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    }
1265569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    return NULL;
1266569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com}
1267569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com
12688a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comvoid SampleWindow::updateTitle() {
12698a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkString title;
12708a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
12718a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkView::F2BIter iter(this);
12728a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkView* view = iter.next();
12738a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkEvent evt(gTitleEvtName);
12748a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    if (view->doQuery(&evt)) {
12758a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        title.set(evt.findString(gTitleEvtName));
12768a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    }
12778a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    if (title.size() == 0) {
12788a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        title.set("<unknown>");
12798a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    }
12802e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
12818a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    title.prepend(gCanvasTypePrefix[fCanvasType]);
12828a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
12838a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    title.prepend(" ");
12848a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    title.prepend(configToString(this->getBitmap().config()));
12852e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
12868a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    if (fAnimating) {
12878a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        title.prepend("<A> ");
12888a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    }
12896c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com    if (fScale) {
12906c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com        title.prepend("<S> ");
12916c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com    }
12926c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com    if (fRotate) {
12936c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com        title.prepend("<R> ");
12946c5f6f25b43f1210decb48956c1a2fbe5b58f889reed@android.com    }
1295e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com    if (fNClip) {
1296e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com        title.prepend("<C> ");
1297e522ca5d5f249bd51a00cb68bb051f811d0a9e85reed@android.com    }
1298569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com
1299569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    title.prepend(trystate_str(fLCDState, "LCD ", "lcd "));
1300569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    title.prepend(trystate_str(fAAState, "AA ", "aa "));
130109e3baaaf54a8a3c701cfc5ad24a8180464a4742reed@google.com    title.prepend(trystate_str(fFilterState, "H ", "h "));
1302569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    title.prepend(fFlipAxis & kFlipAxis_X ? "X " : NULL);
1303569e0435af62bdb88a662fa0592f75673a17afd9reed@google.com    title.prepend(fFlipAxis & kFlipAxis_Y ? "Y " : NULL);
1304dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org
1305dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    if (fZoomLevel) {
1306dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org        title.prependf("{%d} ", fZoomLevel);
1307dd0cd34067d103ace7c6739405cb7885d8ad3fb2mike@reedtribe.org    }
13082eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org
13092eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    if (fMeasureFPS) {
13102eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org        title.appendf(" %4d ms", fMeasureFPS_Time);
13112eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    }
1312a6ff4dc22d5006dc588769aa20c8b0bb4fde6d43reed@google.com    if (fUsePipe && SampleView::IsSampleView(view)) {
1313a6ff4dc22d5006dc588769aa20c8b0bb4fde6d43reed@google.com        title.prepend("<P> ");
1314a6ff4dc22d5006dc588769aa20c8b0bb4fde6d43reed@google.com    }
1315a6ff4dc22d5006dc588769aa20c8b0bb4fde6d43reed@google.com    if (SampleView::IsSampleView(view)) {
1316a6ff4dc22d5006dc588769aa20c8b0bb4fde6d43reed@google.com        title.prepend("! ");
1317a6ff4dc22d5006dc588769aa20c8b0bb4fde6d43reed@google.com    }
13182eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org
13198a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    this->setTitle(title.c_str());
13208a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
13218a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
13228a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comvoid SampleWindow::onSizeChange() {
13238a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    this->INHERITED::onSizeChange();
13248a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
13258a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkView::F2BIter iter(this);
13268a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    SkView* view = iter.next();
13278a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    view->setSize(this->width(), this->height());
13282e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
13298a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    // rebuild our clippath
13308a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    {
13318a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        const SkScalar W = this->width();
13328a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        const SkScalar H = this->height();
13332e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
13348a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        fClipPath.reset();
13358a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com#if 0
13368a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        for (SkScalar y = SK_Scalar1; y < H; y += SkIntToScalar(32)) {
13378a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            SkRect r;
13388a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            r.set(SK_Scalar1, y, SkIntToScalar(30), y + SkIntToScalar(30));
13398a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com            for (; r.fLeft < W; r.offset(SkIntToScalar(32), 0))
13408a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com                fClipPath.addRect(r);
13418a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        }
13428a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com#else
13438a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        SkRect r;
13448a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        r.set(0, 0, W, H);
13458a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        fClipPath.addRect(r, SkPath::kCCW_Direction);
13468a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        r.set(W/4, H/4, W*3/4, H*3/4);
13478a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com        fClipPath.addRect(r, SkPath::kCW_Direction);
13488a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com#endif
13498a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    }
13502e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
13518a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    this->updateTitle();    // to refresh our config
13528a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
13538a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
13548a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com///////////////////////////////////////////////////////////////////////////////
13558a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
1356a6ff4dc22d5006dc588769aa20c8b0bb4fde6d43reed@google.comstatic const char is_sample_view_tag[] = "sample-is-sample-view";
13572eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.orgstatic const char repeat_count_tag[] = "sample-set-repeat-count";
13580faac1e8579088a39f38d02ff675f14d7deb608dreed@google.comstatic const char set_use_pipe_tag[] = "sample-set-use-pipe";
13592eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org
1360a6ff4dc22d5006dc588769aa20c8b0bb4fde6d43reed@google.combool SampleView::IsSampleView(SkView* view) {
1361a6ff4dc22d5006dc588769aa20c8b0bb4fde6d43reed@google.com    SkEvent evt(is_sample_view_tag);
1362a6ff4dc22d5006dc588769aa20c8b0bb4fde6d43reed@google.com    return view->doQuery(&evt);
1363a6ff4dc22d5006dc588769aa20c8b0bb4fde6d43reed@google.com}
1364a6ff4dc22d5006dc588769aa20c8b0bb4fde6d43reed@google.com
1365f21833999d90ad9c8c584cff3238797b39cfc00breed@google.combool SampleView::SetRepeatDraw(SkView* view, int count) {
13662eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    SkEvent evt(repeat_count_tag);
13672eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    evt.setFast32(count);
1368f21833999d90ad9c8c584cff3238797b39cfc00breed@google.com    return view->doEvent(evt);
13692eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org}
13702eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org
13710faac1e8579088a39f38d02ff675f14d7deb608dreed@google.combool SampleView::SetUsePipe(SkView* view, bool pred) {
13720faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com    SkEvent evt(set_use_pipe_tag);
13730faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com    evt.setFast32(pred);
13740faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com    return view->doEvent(evt);
13750faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com}
13760faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com
13772eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.orgbool SampleView::onEvent(const SkEvent& evt) {
13782eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    if (evt.isType(repeat_count_tag)) {
13792eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org        fRepeatCount = evt.getFast32();
13802eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org        return true;
13812eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    }
13820faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com    if (evt.isType(set_use_pipe_tag)) {
13830faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com        fUsePipe = !!evt.getFast32();
13840faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com        return true;
13850faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com    }
13862eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    return this->INHERITED::onEvent(evt);
13872eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org}
13882eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org
13892eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.orgbool SampleView::onQuery(SkEvent* evt) {
1390a6ff4dc22d5006dc588769aa20c8b0bb4fde6d43reed@google.com    if (evt->isType(is_sample_view_tag)) {
1391a6ff4dc22d5006dc588769aa20c8b0bb4fde6d43reed@google.com        return true;
1392a6ff4dc22d5006dc588769aa20c8b0bb4fde6d43reed@google.com    }
13932eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    return this->INHERITED::onQuery(evt);
13942eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org}
13952eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org
13964aebe4fb10ebdfe81192f46906ca53cf6033a467reed@google.com#define TEST_GPIPEx
139764e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com
139868f456d5686c8edbd3da6e7169a983306cc5ee39reed@google.com#ifdef TEST_GPIPE
139968f456d5686c8edbd3da6e7169a983306cc5ee39reed@google.com    #include "SkGPipe.h"
140064e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com
140164e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.comclass SimplePC : public SkGPipeController {
140264e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.compublic:
140364e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    SimplePC(SkCanvas* target);
140464e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    ~SimplePC();
140564e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com
140664e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    virtual void* requestBlock(size_t minRequest, size_t* actual);
140764e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    virtual void notifyWritten(size_t bytes);
140864e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com
140964e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.comprivate:
1410961ddb04a0a7aba843032d829ab867518e52559ereed@google.com    SkGPipeReader   fReader;
1411961ddb04a0a7aba843032d829ab867518e52559ereed@google.com    void*           fBlock;
1412961ddb04a0a7aba843032d829ab867518e52559ereed@google.com    size_t          fBlockSize;
1413961ddb04a0a7aba843032d829ab867518e52559ereed@google.com    size_t          fBytesWritten;
1414961ddb04a0a7aba843032d829ab867518e52559ereed@google.com    int             fAtomsWritten;
141564e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    SkGPipeReader::Status   fStatus;
141664e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com
141764e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    size_t        fTotalWritten;
141864e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com};
141964e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com
142064e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.comSimplePC::SimplePC(SkCanvas* target) : fReader(target) {
142164e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    fBlock = NULL;
142264e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    fBlockSize = fBytesWritten = 0;
142364e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    fStatus = SkGPipeReader::kDone_Status;
142464e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    fTotalWritten = 0;
1425961ddb04a0a7aba843032d829ab867518e52559ereed@google.com    fAtomsWritten = 0;
142664e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com}
142764e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com
142864e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.comSimplePC::~SimplePC() {
142964e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com//    SkASSERT(SkGPipeReader::kDone_Status == fStatus);
143064e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    sk_free(fBlock);
143164e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com
14320faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com    if (fTotalWritten) {
14330faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com        SkDebugf("--- %d bytes %d atoms, status %d\n", fTotalWritten,
14340faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com                 fAtomsWritten, fStatus);
14350faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com    }
143664e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com}
143764e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com
143864e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.comvoid* SimplePC::requestBlock(size_t minRequest, size_t* actual) {
143964e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    sk_free(fBlock);
144064e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com
144164e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    fBlockSize = minRequest * 4;
144264e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    fBlock = sk_malloc_throw(fBlockSize);
144364e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    fBytesWritten = 0;
144464e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    *actual = fBlockSize;
144564e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    return fBlock;
144664e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com}
144764e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com
144864e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.comvoid SimplePC::notifyWritten(size_t bytes) {
144964e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    SkASSERT(fBytesWritten + bytes <= fBlockSize);
145064e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com
145164e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    fStatus = fReader.playback((const char*)fBlock + fBytesWritten, bytes);
145264e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    SkASSERT(SkGPipeReader::kError_Status != fStatus);
145364e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    fBytesWritten += bytes;
145464e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    fTotalWritten += bytes;
1455961ddb04a0a7aba843032d829ab867518e52559ereed@google.com
1456961ddb04a0a7aba843032d829ab867518e52559ereed@google.com    fAtomsWritten += 1;
145764e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com}
145864e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com
145968f456d5686c8edbd3da6e7169a983306cc5ee39reed@google.com#endif
14602f3dc9dc4c970bd066be329a842a791d91f524e2reed@google.com
146164e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com
14622eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.orgvoid SampleView::onDraw(SkCanvas* canvas) {
14632eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    this->onDrawBackground(canvas);
14642f3dc9dc4c970bd066be329a842a791d91f524e2reed@google.com
14652f3dc9dc4c970bd066be329a842a791d91f524e2reed@google.com#ifdef TEST_GPIPE
146664e3eb24e52a84613ff8c1da5dac6f4b5ba38320reed@google.com    SimplePC controller(canvas);
14672f3dc9dc4c970bd066be329a842a791d91f524e2reed@google.com    SkGPipeWriter writer;
14680faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com    if (fUsePipe) {
14690faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com        canvas = writer.startRecording(&controller);
14700faac1e8579088a39f38d02ff675f14d7deb608dreed@google.com    }
14712f3dc9dc4c970bd066be329a842a791d91f524e2reed@google.com#endif
14722f3dc9dc4c970bd066be329a842a791d91f524e2reed@google.com
14732eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    for (int i = 0; i < fRepeatCount; i++) {
14742eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org        SkAutoCanvasRestore acr(canvas, true);
14752eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org        this->onDrawContent(canvas);
14762eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org    }
14772eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org}
14782eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org
14792eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.orgvoid SampleView::onDrawBackground(SkCanvas* canvas) {
1480f21833999d90ad9c8c584cff3238797b39cfc00breed@google.com    canvas->drawColor(fBGColor);
14812eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org}
14822eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org
14832eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org///////////////////////////////////////////////////////////////////////////////
14842eb595292b9624371d1698ae9da7accb4c09c26cmike@reedtribe.org
1485f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.comtemplate <typename T> void SkTBSort(T array[], int count) {
1486f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    for (int i = 1; i < count - 1; i++) {
1487f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        bool didSwap = false;
1488f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        for (int j = count - 1; j > i; --j) {
1489f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            if (array[j] < array[j-1]) {
1490f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com                T tmp(array[j-1]);
1491f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com                array[j-1] = array[j];
1492f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com                array[j] = tmp;
1493f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com                didSwap = true;
1494f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            }
1495f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        }
1496f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        if (!didSwap) {
1497f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            break;
1498f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        }
1499f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    }
15002e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
1501f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    for (int k = 0; k < count - 1; k++) {
1502f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        SkASSERT(!(array[k+1] < array[k]));
1503f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    }
1504f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com}
1505f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
1506f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com#include "SkRandom.h"
1507f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
1508f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.comstatic void rand_rect(SkIRect* rect, SkRandom& rand) {
1509f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    int bits = 8;
1510f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    int shift = 32 - bits;
1511f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    rect->set(rand.nextU() >> shift, rand.nextU() >> shift,
1512f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com              rand.nextU() >> shift, rand.nextU() >> shift);
1513f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    rect->sort();
1514f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com}
1515f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
1516f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.comstatic void dumpRect(const SkIRect& r) {
1517f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    SkDebugf(" { %d, %d, %d, %d },\n",
1518f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com             r.fLeft, r.fTop,
1519f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com             r.fRight, r.fBottom);
1520f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com}
1521f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
1522f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.comstatic void test_rects(const SkIRect rect[], int count) {
1523f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    SkRegion rgn0, rgn1;
1524f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
1525f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    for (int i = 0; i < count; i++) {
1526f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        rgn0.op(rect[i], SkRegion::kUnion_Op);
1527f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com     //   dumpRect(rect[i]);
1528f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    }
1529f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    rgn1.setRects(rect, count);
1530f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
1531f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    if (rgn0 != rgn1) {
1532f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        SkDebugf("\n");
1533f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        for (int i = 0; i < count; i++) {
1534f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            dumpRect(rect[i]);
1535f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        }
1536f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        SkDebugf("\n");
1537f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    }
1538f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com}
1539f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
1540f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.comstatic void test() {
1541f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    size_t i;
1542f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
1543f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    const SkIRect r0[] = {
1544f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        { 0, 0, 1, 1 },
1545f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        { 2, 2, 3, 3 },
1546f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    };
1547f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    const SkIRect r1[] = {
1548f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        { 0, 0, 1, 3 },
1549f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        { 1, 1, 2, 2 },
1550f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        { 2, 0, 3, 3 },
1551f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    };
1552f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    const SkIRect r2[] = {
1553f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        { 0, 0, 1, 2 },
1554f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        { 2, 1, 3, 3 },
1555f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        { 4, 0, 5, 1 },
1556f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        { 6, 0, 7, 4 },
1557f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    };
1558f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
1559f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    static const struct {
1560f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        const SkIRect* fRects;
1561f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        int            fCount;
1562f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    } gRecs[] = {
1563f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        { r0, SK_ARRAY_COUNT(r0) },
1564f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        { r1, SK_ARRAY_COUNT(r1) },
1565f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        { r2, SK_ARRAY_COUNT(r2) },
1566f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    };
1567f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
1568f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    for (i = 0; i < SK_ARRAY_COUNT(gRecs); i++) {
1569f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        test_rects(gRecs[i].fRects, gRecs[i].fCount);
1570f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    }
15712e7b43d33cc495663cb814a7a9d1ecdc09c31828bsalomon@google.com
1572f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    SkRandom rand;
1573f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    for (i = 0; i < 10000; i++) {
1574f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        SkRegion rgn0, rgn1;
1575f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
1576f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        const int N = 8;
1577f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        SkIRect rect[N];
1578f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        for (int j = 0; j < N; j++) {
1579f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com            rand_rect(&rect[j], rand);
1580f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        }
1581f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com        test_rects(rect, N);
1582f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com    }
1583f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com}
1584f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com
15858a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comSkOSWindow* create_sk_window(void* hwnd) {
1586f2b98d67dcb6fcb3120feede9c72016fc7b3ead8reed@android.com//    test();
15872fbc7fa460c99bffa78b9afb9aaa4dc0db68e1babsalomon@google.com    return new SampleWindow(hwnd);
15888a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
15898a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
15908a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comvoid get_preferred_size(int* x, int* y, int* width, int* height) {
15918a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    *x = 10;
15928a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    *y = 50;
15938a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    *width = 640;
15948a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    *height = 480;
15958a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
15968a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
15978a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comvoid application_init() {
15988a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com//    setenv("ANDROID_ROOT", "../../../data", 0);
1599e191b16fda2f5afea3a90653c1cd4f5a3c436e89reed@android.com#ifdef SK_BUILD_FOR_MAC
16008a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com    setenv("ANDROID_ROOT", "/android/device/data", 0);
1601e191b16fda2f5afea3a90653c1cd4f5a3c436e89reed@android.com#endif
16022fbc7fa460c99bffa78b9afb9aaa4dc0db68e1babsalomon@google.com    SkGraphics::Init();
16032fbc7fa460c99bffa78b9afb9aaa4dc0db68e1babsalomon@google.com    SkEvent::Init();
16048a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
16058a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com
16068a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.comvoid application_term() {
16072fbc7fa460c99bffa78b9afb9aaa4dc0db68e1babsalomon@google.com    SkEvent::Term();
16082fbc7fa460c99bffa78b9afb9aaa4dc0db68e1babsalomon@google.com    SkGraphics::Term();
16098a1c16ff38322f0210116fa7293eb8817c7e477ereed@android.com}
1610