blob: 9ea1d9e47999658fea77fd374453c4067bd73f70 [file] [log] [blame]
mike@reedtribe.org50e4c722012-10-22 03:59:34 +00001/*
2 * Copyright 2012 Google Inc.
3 *
4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file.
6 */
7
8#include "SampleCode.h"
9#include "SkView.h"
10#include "SkCanvas.h"
11#include "SkPath.h"
12#include "SkRegion.h"
13#include "SkShader.h"
14#include "SkUtils.h"
15#include "SkImage.h"
16#include "SkSurface.h"
17
reed@google.comc83e3522012-10-22 22:00:08 +000018#define FAT_PIXEL_COLOR SK_ColorBLACK
19#define PIXEL_CENTER_SIZE 3
20#define WIRE_FRAME_COLOR 0xFFFF0000 /*0xFF00FFFF*/
21#define WIRE_FRAME_SIZE 1.5f
22
reed@google.combbe66f02013-10-30 13:41:19 +000023static SkScalar apply_grid(SkScalar x) {
24 const SkScalar grid = 2;
25 return SkScalarRoundToScalar(x * grid) / grid;
26}
27
28static void apply_grid(SkPoint pts[], int count) {
29 for (int i = 0; i < count; ++i) {
30 pts[i].set(apply_grid(pts[i].fX), apply_grid(pts[i].fY));
31 }
32}
33
mike@reedtribe.org50e4c722012-10-22 03:59:34 +000034static void erase(SkSurface* surface) {
junov@google.comdbfac8a2012-12-06 21:47:40 +000035 surface->getCanvas()->clear(SK_ColorTRANSPARENT);
mike@reedtribe.org50e4c722012-10-22 03:59:34 +000036}
37
38static SkShader* createChecker() {
reed@google.com9c0bef12012-11-02 19:59:18 +000039// SkColor colors[] = { 0xFFFDFDFD, 0xFFF4F4F4 };
40 SkColor colors[] = { 0xFFFFFFFF, 0xFFFFFFFF };
mike@reedtribe.org50e4c722012-10-22 03:59:34 +000041 SkBitmap bm;
commit-bot@chromium.orga8c18312014-02-17 02:55:57 +000042 bm.allocN32Pixels(2, 2);
mike@reedtribe.org50e4c722012-10-22 03:59:34 +000043 bm.lockPixels();
reed@google.com9c0bef12012-11-02 19:59:18 +000044 *bm.getAddr32(0, 0) = *bm.getAddr32(1, 1) = SkPreMultiplyColor(colors[0]);
45 *bm.getAddr32(0, 1) = *bm.getAddr32(1, 0) = SkPreMultiplyColor(colors[1]);
mike@reedtribe.org50e4c722012-10-22 03:59:34 +000046 SkMatrix m;
47 m.setScale(12, 12);
commit-bot@chromium.org9c9005a2014-04-28 14:55:39 +000048 return SkShader::CreateBitmapShader(bm, SkShader::kRepeat_TileMode,
49 SkShader::kRepeat_TileMode, &m);
mike@reedtribe.org50e4c722012-10-22 03:59:34 +000050}
51
52class FatBits {
53public:
54 FatBits() : fShader(createChecker()) {
55 fAA = false;
56 fStyle = kHair_Style;
57 fGrid = true;
reed@google.comc83e3522012-10-22 22:00:08 +000058 fShowSkeleton = true;
59 fUseGPU = false;
reed@google.com9c0bef12012-11-02 19:59:18 +000060 fUseClip = false;
mike@reedtribe.org64494e92013-03-06 02:18:33 +000061 fRectAsOval = false;
reed@google.combbe66f02013-10-30 13:41:19 +000062 fUseTriangle = false;
skia.committer@gmail.com1aa90cf2012-11-06 13:18:25 +000063
reed@google.com9c0bef12012-11-02 19:59:18 +000064 fClipRect.set(2, 2, 11, 8 );
mike@reedtribe.org50e4c722012-10-22 03:59:34 +000065 }
66
robertphillips@google.comca47aae2012-12-12 15:58:25 +000067 int getZoom() const { return fZoom; }
reed@google.comc83e3522012-10-22 22:00:08 +000068
mike@reedtribe.org50e4c722012-10-22 03:59:34 +000069 bool getAA() const { return fAA; }
70 void setAA(bool aa) { fAA = aa; }
71
72 bool getGrid() const { return fGrid; }
73 void setGrid(bool g) { fGrid = g; }
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +000074
reed@google.comc83e3522012-10-22 22:00:08 +000075 bool getShowSkeleton() const { return fShowSkeleton; }
76 void setShowSkeleton(bool ss) { fShowSkeleton = ss; }
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +000077
reed@google.comc83e3522012-10-22 22:00:08 +000078 bool getUseGPU() const { return fUseGPU; }
79 void setUseGPU(bool ug) { fUseGPU = ug; }
skia.committer@gmail.com7ed98df2013-10-31 07:01:53 +000080
reed@google.combbe66f02013-10-30 13:41:19 +000081 bool getTriangle() const { return fUseTriangle; }
82 void setTriangle(bool ut) { fUseTriangle = ut; }
skia.committer@gmail.com7ed98df2013-10-31 07:01:53 +000083
mike@reedtribe.org64494e92013-03-06 02:18:33 +000084 void toggleRectAsOval() { fRectAsOval = !fRectAsOval; }
85
reed@google.com9c0bef12012-11-02 19:59:18 +000086 bool getUseClip() const { return fUseClip; }
87 void setUseClip(bool uc) { fUseClip = uc; }
88
mike@reedtribe.org50e4c722012-10-22 03:59:34 +000089 enum Style {
90 kHair_Style,
reed@google.comc83e3522012-10-22 22:00:08 +000091 kStroke_Style,
mike@reedtribe.org50e4c722012-10-22 03:59:34 +000092 };
93 Style getStyle() const { return fStyle; }
94 void setStyle(Style s) { fStyle = s; }
95
96 void setWHZ(int width, int height, int zoom) {
97 fW = width;
98 fH = height;
robertphillips@google.comca47aae2012-12-12 15:58:25 +000099 fZoom = zoom;
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000100 fBounds.set(0, 0, SkIntToScalar(width * zoom), SkIntToScalar(height * zoom));
101 fMatrix.setScale(SkIntToScalar(zoom), SkIntToScalar(zoom));
102 fInverse.setScale(SK_Scalar1 / zoom, SK_Scalar1 / zoom);
103 fShader->setLocalMatrix(fMatrix);
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000104
commit-bot@chromium.org32678d92014-01-15 02:38:22 +0000105 SkImageInfo info = SkImageInfo::MakeN32Premul(width, height);
reed@google.combbe66f02013-10-30 13:41:19 +0000106 fMinSurface.reset(SkSurface::NewRaster(info));
107 info.fWidth *= zoom;
108 info.fHeight *= zoom;
109 fMaxSurface.reset(SkSurface::NewRaster(info));
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000110 }
111
112 void drawBG(SkCanvas*);
113 void drawFG(SkCanvas*);
114 void drawLine(SkCanvas*, SkPoint pts[2]);
115 void drawRect(SkCanvas* canvas, SkPoint pts[2]);
reed@google.combbe66f02013-10-30 13:41:19 +0000116 void drawTriangle(SkCanvas* canvas, SkPoint pts[3]);
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000117
118private:
reed@google.combbe66f02013-10-30 13:41:19 +0000119 bool fAA, fGrid, fShowSkeleton, fUseGPU, fUseClip, fRectAsOval, fUseTriangle;
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000120 Style fStyle;
robertphillips@google.comca47aae2012-12-12 15:58:25 +0000121 int fW, fH, fZoom;
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000122 SkMatrix fMatrix, fInverse;
reed@google.com9c0bef12012-11-02 19:59:18 +0000123 SkRect fBounds, fClipRect;
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000124 SkAutoTUnref<SkShader> fShader;
125 SkAutoTUnref<SkSurface> fMinSurface;
126 SkAutoTUnref<SkSurface> fMaxSurface;
127
128 void setupPaint(SkPaint* paint) {
129 bool aa = this->getAA();
130 switch (fStyle) {
131 case kHair_Style:
132 paint->setStrokeWidth(0);
133 break;
134 case kStroke_Style:
reed@google.comcdbcb3e2012-10-22 22:10:20 +0000135 paint->setStrokeWidth(SK_Scalar1);
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000136 break;
137 }
138 paint->setAntiAlias(aa);
139 }
140
reed@google.comc83e3522012-10-22 22:00:08 +0000141 void setupSkeletonPaint(SkPaint* paint) {
142 paint->setStyle(SkPaint::kStroke_Style);
143 paint->setStrokeWidth(WIRE_FRAME_SIZE);
144 paint->setColor(fShowSkeleton ? WIRE_FRAME_COLOR : 0);
145 paint->setAntiAlias(true);
146 }
147
reed@google.combbe66f02013-10-30 13:41:19 +0000148 void drawTriangleSkeleton(SkCanvas* max, const SkPoint pts[]);
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000149 void drawLineSkeleton(SkCanvas* max, const SkPoint pts[]);
150 void drawRectSkeleton(SkCanvas* max, const SkRect& r) {
151 SkPaint paint;
reed@google.comc83e3522012-10-22 22:00:08 +0000152 this->setupSkeletonPaint(&paint);
153 SkPath path;
154
155 if (fUseGPU && fAA) {
156 SkRect rr = r;
robertphillips@google.comca47aae2012-12-12 15:58:25 +0000157 rr.inset(SkIntToScalar(fZoom)/2, SkIntToScalar(fZoom)/2);
reed@google.comc83e3522012-10-22 22:00:08 +0000158 path.addRect(rr);
159 path.moveTo(rr.fLeft, rr.fTop);
160 path.lineTo(rr.fRight, rr.fBottom);
161 rr = r;
robertphillips@google.comca47aae2012-12-12 15:58:25 +0000162 rr.inset(-SkIntToScalar(fZoom)/2, -SkIntToScalar(fZoom)/2);
reed@google.comc83e3522012-10-22 22:00:08 +0000163 path.addRect(rr);
164 } else {
mike@reedtribe.org64494e92013-03-06 02:18:33 +0000165 fRectAsOval ? path.addOval(r) : path.addRect(r);
reed@google.comc83e3522012-10-22 22:00:08 +0000166 if (fUseGPU) {
167 path.moveTo(r.fLeft, r.fTop);
168 path.lineTo(r.fRight, r.fBottom);
169 }
170 }
171 max->drawPath(path, paint);
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000172 }
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000173
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000174 void copyMinToMax() {
175 erase(fMaxSurface);
176 SkCanvas* canvas = fMaxSurface->getCanvas();
177 canvas->save();
178 canvas->concat(fMatrix);
179 fMinSurface->draw(canvas, 0, 0, NULL);
180 canvas->restore();
181
182 SkPaint paint;
183 paint.setXfermodeMode(SkXfermode::kClear_Mode);
184 for (int iy = 1; iy < fH; ++iy) {
robertphillips@google.comca47aae2012-12-12 15:58:25 +0000185 SkScalar y = SkIntToScalar(iy * fZoom);
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000186 canvas->drawLine(0, y - SK_ScalarHalf, 999, y - SK_ScalarHalf, paint);
187 }
188 for (int ix = 1; ix < fW; ++ix) {
robertphillips@google.comca47aae2012-12-12 15:58:25 +0000189 SkScalar x = SkIntToScalar(ix * fZoom);
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000190 canvas->drawLine(x - SK_ScalarHalf, 0, x - SK_ScalarHalf, 999, paint);
191 }
192 }
193};
194
195void FatBits::drawBG(SkCanvas* canvas) {
196 SkPaint paint;
197
198 paint.setShader(fShader);
199 canvas->drawRect(fBounds, paint);
200 paint.setShader(NULL);
201}
202
203void FatBits::drawFG(SkCanvas* canvas) {
reed@google.comc83e3522012-10-22 22:00:08 +0000204 SkPaint inner, outer;
205
206 inner.setAntiAlias(true);
207 inner.setColor(SK_ColorBLACK);
208 inner.setStrokeWidth(PIXEL_CENTER_SIZE);
209
210 outer.setAntiAlias(true);
211 outer.setColor(SK_ColorWHITE);
212 outer.setStrokeWidth(PIXEL_CENTER_SIZE + 2);
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000213
robertphillips@google.comca47aae2012-12-12 15:58:25 +0000214 SkScalar half = SkIntToScalar(fZoom) / 2;
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000215 for (int iy = 0; iy < fH; ++iy) {
robertphillips@google.comca47aae2012-12-12 15:58:25 +0000216 SkScalar y = SkIntToScalar(iy * fZoom) + half;
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000217 for (int ix = 0; ix < fW; ++ix) {
robertphillips@google.comca47aae2012-12-12 15:58:25 +0000218 SkScalar x = SkIntToScalar(ix * fZoom) + half;
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000219
reed@google.comc83e3522012-10-22 22:00:08 +0000220 canvas->drawPoint(x, y, outer);
221 canvas->drawPoint(x, y, inner);
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000222 }
223 }
reed@google.com9c0bef12012-11-02 19:59:18 +0000224
225 if (fUseClip) {
226 SkPaint p;
227 p.setStyle(SkPaint::kStroke_Style);
228 p.setColor(SK_ColorLTGRAY);
229 SkRect r = {
robertphillips@google.comca47aae2012-12-12 15:58:25 +0000230 fClipRect.fLeft * fZoom,
231 fClipRect.fTop * fZoom,
232 fClipRect.fRight * fZoom,
233 fClipRect.fBottom * fZoom
reed@google.com9c0bef12012-11-02 19:59:18 +0000234 };
235 canvas->drawRect(r, p);
236 }
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000237}
238
239void FatBits::drawLineSkeleton(SkCanvas* max, const SkPoint pts[]) {
240 SkPaint paint;
reed@google.comc83e3522012-10-22 22:00:08 +0000241 this->setupSkeletonPaint(&paint);
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000242
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000243 SkPath path;
244 path.moveTo(pts[0]);
245 path.lineTo(pts[1]);
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000246
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000247 switch (fStyle) {
248 case kHair_Style:
reed@google.comc83e3522012-10-22 22:00:08 +0000249 if (fUseGPU) {
250 SkPaint p;
251 p.setStyle(SkPaint::kStroke_Style);
robertphillips@google.comca47aae2012-12-12 15:58:25 +0000252 p.setStrokeWidth(SK_Scalar1 * fZoom);
reed@google.comc83e3522012-10-22 22:00:08 +0000253 SkPath dst;
254 p.getFillPath(path, &dst);
255 path.addPath(dst);
256 }
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000257 break;
258 case kStroke_Style: {
259 SkPaint p;
260 p.setStyle(SkPaint::kStroke_Style);
robertphillips@google.comca47aae2012-12-12 15:58:25 +0000261 p.setStrokeWidth(SK_Scalar1 * fZoom);
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000262 SkPath dst;
263 p.getFillPath(path, &dst);
264 path = dst;
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000265
reed@google.comc83e3522012-10-22 22:00:08 +0000266 if (fUseGPU) {
267 path.moveTo(dst.getPoint(0));
268 path.lineTo(dst.getPoint(2));
269 }
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000270 } break;
271 }
272 max->drawPath(path, paint);
273}
274
275void FatBits::drawLine(SkCanvas* canvas, SkPoint pts[]) {
276 SkPaint paint;
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000277
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000278 fInverse.mapPoints(pts, 2);
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000279
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000280 if (fGrid) {
reed@google.combbe66f02013-10-30 13:41:19 +0000281 apply_grid(pts, 2);
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000282 }
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000283
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000284 erase(fMinSurface);
285 this->setupPaint(&paint);
reed@google.comc83e3522012-10-22 22:00:08 +0000286 paint.setColor(FAT_PIXEL_COLOR);
reed@google.com9c0bef12012-11-02 19:59:18 +0000287 if (fUseClip) {
288 fMinSurface->getCanvas()->save();
289 SkRect r = fClipRect;
290 r.inset(SK_Scalar1/3, SK_Scalar1/3);
291 fMinSurface->getCanvas()->clipRect(r, SkRegion::kIntersect_Op, true);
292 }
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000293 fMinSurface->getCanvas()->drawLine(pts[0].fX, pts[0].fY, pts[1].fX, pts[1].fY, paint);
reed@google.com9c0bef12012-11-02 19:59:18 +0000294 if (fUseClip) {
295 fMinSurface->getCanvas()->restore();
296 }
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000297 this->copyMinToMax();
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000298
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000299 SkCanvas* max = fMaxSurface->getCanvas();
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000300
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000301 fMatrix.mapPoints(pts, 2);
302 this->drawLineSkeleton(max, pts);
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000303
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000304 fMaxSurface->draw(canvas, 0, 0, NULL);
305}
306
307void FatBits::drawRect(SkCanvas* canvas, SkPoint pts[2]) {
308 SkPaint paint;
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000309
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000310 fInverse.mapPoints(pts, 2);
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000311
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000312 if (fGrid) {
reed@google.combbe66f02013-10-30 13:41:19 +0000313 apply_grid(pts, 2);
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000314 }
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000315
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000316 SkRect r;
317 r.set(pts, 2);
318
319 erase(fMinSurface);
320 this->setupPaint(&paint);
reed@google.comc83e3522012-10-22 22:00:08 +0000321 paint.setColor(FAT_PIXEL_COLOR);
mike@reedtribe.org64494e92013-03-06 02:18:33 +0000322 {
323 SkCanvas* c = fMinSurface->getCanvas();
324 fRectAsOval ? c->drawOval(r, paint) : c->drawRect(r, paint);
325 }
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000326 this->copyMinToMax();
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000327
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000328 SkCanvas* max = fMaxSurface->getCanvas();
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000329
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000330 fMatrix.mapPoints(pts, 2);
331 r.set(pts, 2);
332 this->drawRectSkeleton(max, r);
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000333
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000334 fMaxSurface->draw(canvas, 0, 0, NULL);
335}
336
reed@google.combbe66f02013-10-30 13:41:19 +0000337void FatBits::drawTriangleSkeleton(SkCanvas* max, const SkPoint pts[]) {
338 SkPaint paint;
339 this->setupSkeletonPaint(&paint);
skia.committer@gmail.com7ed98df2013-10-31 07:01:53 +0000340
reed@google.combbe66f02013-10-30 13:41:19 +0000341 SkPath path;
342 path.moveTo(pts[0]);
343 path.lineTo(pts[1]);
344 path.lineTo(pts[2]);
345 path.close();
skia.committer@gmail.com7ed98df2013-10-31 07:01:53 +0000346
reed@google.combbe66f02013-10-30 13:41:19 +0000347 max->drawPath(path, paint);
348}
349
350void FatBits::drawTriangle(SkCanvas* canvas, SkPoint pts[3]) {
351 SkPaint paint;
skia.committer@gmail.com7ed98df2013-10-31 07:01:53 +0000352
reed@google.combbe66f02013-10-30 13:41:19 +0000353 fInverse.mapPoints(pts, 3);
skia.committer@gmail.com7ed98df2013-10-31 07:01:53 +0000354
reed@google.combbe66f02013-10-30 13:41:19 +0000355 if (fGrid) {
356 apply_grid(pts, 3);
357 }
skia.committer@gmail.com7ed98df2013-10-31 07:01:53 +0000358
reed@google.combbe66f02013-10-30 13:41:19 +0000359 SkPath path;
360 path.moveTo(pts[0]);
361 path.lineTo(pts[1]);
362 path.lineTo(pts[2]);
363 path.close();
skia.committer@gmail.com7ed98df2013-10-31 07:01:53 +0000364
reed@google.combbe66f02013-10-30 13:41:19 +0000365 erase(fMinSurface);
366 this->setupPaint(&paint);
367 paint.setColor(FAT_PIXEL_COLOR);
368 fMinSurface->getCanvas()->drawPath(path, paint);
369 this->copyMinToMax();
skia.committer@gmail.com7ed98df2013-10-31 07:01:53 +0000370
reed@google.combbe66f02013-10-30 13:41:19 +0000371 SkCanvas* max = fMaxSurface->getCanvas();
skia.committer@gmail.com7ed98df2013-10-31 07:01:53 +0000372
reed@google.combbe66f02013-10-30 13:41:19 +0000373 fMatrix.mapPoints(pts, 3);
374 this->drawTriangleSkeleton(max, pts);
skia.committer@gmail.com7ed98df2013-10-31 07:01:53 +0000375
reed@google.combbe66f02013-10-30 13:41:19 +0000376 fMaxSurface->draw(canvas, 0, 0, NULL);
377}
378
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000379///////////////////////////////////////////////////////////////////////////////////////////////////
380
381class IndexClick : public SkView::Click {
382 int fIndex;
383public:
384 IndexClick(SkView* v, int index) : SkView::Click(v), fIndex(index) {}
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000385
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000386 static int GetIndex(SkView::Click* click) {
387 return ((IndexClick*)click)->fIndex;
388 }
389};
390
391class DrawLineView : public SampleView {
392 FatBits fFB;
reed@google.combbe66f02013-10-30 13:41:19 +0000393 SkPoint fPts[3];
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000394 bool fIsRect;
395public:
396 DrawLineView() {
397 fFB.setWHZ(24, 16, 48);
reed@google.comcdbcb3e2012-10-22 22:10:20 +0000398 fPts[0].set(48, 48);
399 fPts[1].set(48 * 5, 48 * 4);
reed@google.combbe66f02013-10-30 13:41:19 +0000400 fPts[2].set(48 * 2, 48 * 6);
reed@google.comcdbcb3e2012-10-22 22:10:20 +0000401 fIsRect = false;
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000402 }
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000403
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000404 void setStyle(FatBits::Style s) {
405 fFB.setStyle(s);
406 this->inval(NULL);
407 }
408
409protected:
410 virtual bool onQuery(SkEvent* evt) SK_OVERRIDE {
411 if (SampleCode::TitleQ(*evt)) {
412 SampleCode::TitleR(evt, "FatBits");
413 return true;
414 }
415 SkUnichar uni;
416 if (SampleCode::CharQ(*evt, &uni)) {
417 switch (uni) {
reed@google.com9c0bef12012-11-02 19:59:18 +0000418 case 'c':
419 fFB.setUseClip(!fFB.getUseClip());
420 this->inval(NULL);
421 return true;
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000422 case 'r':
423 fIsRect = !fIsRect;
424 this->inval(NULL);
425 return true;
mike@reedtribe.org64494e92013-03-06 02:18:33 +0000426 case 'o':
427 fFB.toggleRectAsOval();
428 this->inval(NULL);
429 return true;
reed@google.comc83e3522012-10-22 22:00:08 +0000430 case 'x':
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000431 fFB.setGrid(!fFB.getGrid());
432 this->inval(NULL);
433 return true;
434 case 's':
435 if (FatBits::kStroke_Style == fFB.getStyle()) {
436 this->setStyle(FatBits::kHair_Style);
437 } else {
438 this->setStyle(FatBits::kStroke_Style);
439 }
440 return true;
441 case 'a':
442 fFB.setAA(!fFB.getAA());
443 this->inval(NULL);
444 return true;
reed@google.comc83e3522012-10-22 22:00:08 +0000445 case 'w':
446 fFB.setShowSkeleton(!fFB.getShowSkeleton());
447 this->inval(NULL);
448 return true;
449 case 'g':
450 fFB.setUseGPU(!fFB.getUseGPU());
451 this->inval(NULL);
452 return true;
reed@google.combbe66f02013-10-30 13:41:19 +0000453 case 't':
454 fFB.setTriangle(!fFB.getTriangle());
455 this->inval(NULL);
456 return true;
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000457 }
458 }
459 return this->INHERITED::onQuery(evt);
460 }
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000461
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000462 virtual void onDrawContent(SkCanvas* canvas) {
463 fFB.drawBG(canvas);
reed@google.combbe66f02013-10-30 13:41:19 +0000464 if (fFB.getTriangle()) {
465 fFB.drawTriangle(canvas, fPts);
466 }
467 else if (fIsRect) {
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000468 fFB.drawRect(canvas, fPts);
469 } else {
470 fFB.drawLine(canvas, fPts);
471 }
472 fFB.drawFG(canvas);
skia.committer@gmail.com1e34ff72012-10-24 02:01:24 +0000473
reed@google.comffe9d012012-10-23 15:33:41 +0000474 {
475 SkString str;
reed@google.com9c0bef12012-11-02 19:59:18 +0000476 str.printf("%s %s %s %s",
reed@google.comffe9d012012-10-23 15:33:41 +0000477 fFB.getAA() ? "AA" : "BW",
478 FatBits::kHair_Style == fFB.getStyle() ? "Hair" : "Stroke",
reed@google.com9c0bef12012-11-02 19:59:18 +0000479 fFB.getUseGPU() ? "GPU" : "CPU",
480 fFB.getUseClip() ? "clip" : "noclip");
reed@google.comffe9d012012-10-23 15:33:41 +0000481 SkPaint paint;
482 paint.setAntiAlias(true);
483 paint.setTextSize(16);
484 paint.setColor(SK_ColorBLUE);
485 canvas->drawText(str.c_str(), str.size(), 10, 16, paint);
486 }
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000487 }
488
mike@reedtribe.org093455c2013-01-28 02:21:27 +0000489 virtual SkView::Click* onFindClickHandler(SkScalar x, SkScalar y,
490 unsigned modi) SK_OVERRIDE {
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000491 SkPoint pt = { x, y };
492 int index = -1;
reed@google.combbe66f02013-10-30 13:41:19 +0000493 int count = fFB.getTriangle() ? 3 : 2;
reed@google.comcdbcb3e2012-10-22 22:10:20 +0000494 SkScalar tol = 12;
skia.committer@gmail.com7ed98df2013-10-31 07:01:53 +0000495
reed@google.combbe66f02013-10-30 13:41:19 +0000496 for (int i = 0; i < count; ++i) {
497 if (fPts[i].equalsWithinTolerance(pt, tol)) {
498 index = i;
499 break;
500 }
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000501 }
mike@reedtribe.orgc892a152012-10-23 03:10:46 +0000502 return new IndexClick(this, index);
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000503 }
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000504
mike@reedtribe.org093455c2013-01-28 02:21:27 +0000505 virtual bool onClick(Click* click) SK_OVERRIDE {
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000506 int index = IndexClick::GetIndex(click);
reed@google.combbe66f02013-10-30 13:41:19 +0000507 if (index >= 0 && index <= 2) {
mike@reedtribe.orgc892a152012-10-23 03:10:46 +0000508 fPts[index] = click->fCurr;
509 } else {
510 SkScalar dx = click->fCurr.fX - click->fPrev.fX;
511 SkScalar dy = click->fCurr.fY - click->fPrev.fY;
512 fPts[0].offset(dx, dy);
513 fPts[1].offset(dx, dy);
reed@google.combbe66f02013-10-30 13:41:19 +0000514 fPts[2].offset(dx, dy);
mike@reedtribe.orgc892a152012-10-23 03:10:46 +0000515 }
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000516 this->inval(NULL);
517 return true;
518 }
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000519
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000520private:
skia.committer@gmail.com45ba2f72012-10-23 02:01:22 +0000521
mike@reedtribe.org50e4c722012-10-22 03:59:34 +0000522 typedef SampleView INHERITED;
523};
524
525//////////////////////////////////////////////////////////////////////////////
526
527static SkView* MyFactory() { return new DrawLineView; }
528static SkViewRegister reg(MyFactory);