blob: 9d368a2e5e5b9459c12a5f71d3f2113b05bb8776 [file] [log] [blame]
epoger@google.comec3ed6a2011-07-28 14:26:00 +00001
2/*
3 * Copyright 2011 Google Inc.
4 *
5 * Use of this source code is governed by a BSD-style license that can be
6 * found in the LICENSE file.
7 */
bsalomon@google.com271cffc2011-05-20 14:13:56 +00008#include "SampleCode.h"
9#include "SkView.h"
10#include "SkCanvas.h"
11#include "Sk64.h"
12#include "SkCornerPathEffect.h"
13#include "SkGradientShader.h"
14#include "SkGraphics.h"
15#include "SkImageDecoder.h"
16#include "SkKernel33MaskFilter.h"
17#include "SkPath.h"
18#include "SkRandom.h"
19#include "SkRegion.h"
20#include "SkShader.h"
21#include "SkUtils.h"
22#include "SkColorPriv.h"
23#include "SkColorFilter.h"
24#include "SkTime.h"
25#include "SkTypeface.h"
26#include "SkXfermode.h"
27
28#include "SkStream.h"
29#include "SkXMLParser.h"
30#include "SkColorPriv.h"
31#include "SkImageDecoder.h"
32#include "SkBlurMaskFilter.h"
33
reed@google.com045e62d2011-10-24 12:19:46 +000034#ifdef SK_BUILD_FOR_MAC
35#import <ApplicationServices/ApplicationServices.h>
36SkTypeface* SkCreateTypefaceFromCTFont(CTFontRef fontRef);
37#endif
38
bsalomon@google.com271cffc2011-05-20 14:13:56 +000039static void setNamedTypeface(SkPaint* paint, const char name[]) {
40 SkTypeface* face = SkTypeface::CreateFromName(name, SkTypeface::kNormal);
41 paint->setTypeface(face);
42 SkSafeUnref(face);
43}
44
45static uint16_t gBG[] = { 0xFFFF, 0xCCCF, 0xCCCF, 0xFFFF };
46
47class XfermodesBlurView : public SampleView {
48 SkBitmap fBG;
49 SkBitmap fSrcB, fDstB;
50
51 void draw_mode(SkCanvas* canvas, SkXfermode* mode, int alpha,
52 SkScalar x, SkScalar y) {
53 SkPaint p;
54 SkMaskFilter* mf = SkBlurMaskFilter::Create(5, SkBlurMaskFilter::kNormal_BlurStyle, 0);
55 p.setMaskFilter(mf)->unref();
56
57 SkScalar ww = SkIntToScalar(W);
58 SkScalar hh = SkIntToScalar(H);
59
60 // draw a circle covering the upper
61 // left three quarters of the canvas
62 p.setColor(0xFFCC44FF);
63 SkRect r;
64 r.set(0, 0, ww*3/4, hh*3/4);
65 r.offset(x, y);
66 canvas->drawOval(r, p);
67
68 p.setXfermode(mode);
69
70 // draw a square overlapping the circle
71 // in the lower right of the canvas
72 p.setColor(0x00AA6633 | alpha << 24);
73 r.set(ww/3, hh/3, ww*19/20, hh*19/20);
74 r.offset(x, y);
75 canvas->drawRect(r, p);
reed@google.com045e62d2011-10-24 12:19:46 +000076
77#ifdef SK_BUILD_FOR_MAC
78 static const char* gNames[] = { "Arial", "Times", "Courier", "Lucida" };
caryclark@google.com02939ce2012-06-06 12:09:51 +000079 for (size_t j = 0; j < SK_ARRAY_COUNT(gNames); ++j) {
reed@google.com045e62d2011-10-24 12:19:46 +000080 CFStringRef name = CFStringCreateWithCString(NULL, gNames[j], kCFStringEncodingUTF8);
81 CTFontRef font = CTFontCreateWithName(name, 0, NULL);
82 SkTypeface* face = SkCreateTypefaceFromCTFont(font);
83 SkDebugf("%s ct:%p face:%p ats:%p\n", gNames[j], font, face, CTFontGetPlatformFont(font, NULL));
84 for (int i = 9; i <= 24; ++i) {
85 CTFontRef newFont = CTFontCreateCopyWithAttributes(font, i, NULL, NULL);
86 SkTypeface* newFace = SkCreateTypefaceFromCTFont(newFont);
87 SkDebugf("size:%d ct:%p face:%p ats:%p\n", i, newFont, newFace, CTFontGetPlatformFont(newFont, NULL));
88 newFace->unref();
89 CFRelease(newFont);
90 }
91 face->unref();
92 CFRelease(font);
93 CFRelease(name);
94 }
95#endif
bsalomon@google.com271cffc2011-05-20 14:13:56 +000096 }
97
98public:
99 const static int W = 64;
100 const static int H = 64;
bsalomon@google.com22c5dea2011-07-07 14:38:03 +0000101 XfermodesBlurView() {
bsalomon@google.com271cffc2011-05-20 14:13:56 +0000102 fBG.setConfig(SkBitmap::kARGB_4444_Config, 2, 2, 4);
103 fBG.setPixels(gBG);
104 fBG.setIsOpaque(true);
105 }
106
107protected:
108 // overrides from SkEventSink
109 virtual bool onQuery(SkEvent* evt) {
110 if (SampleCode::TitleQ(*evt)) {
111 SampleCode::TitleR(evt, "XfermodesBlur");
112 return true;
113 }
114 return this->INHERITED::onQuery(evt);
115 }
116
117 virtual void onDrawContent(SkCanvas* canvas) {
bsalomon@google.com271cffc2011-05-20 14:13:56 +0000118 canvas->translate(SkIntToScalar(10), SkIntToScalar(20));
119
reed@google.com87fac4a2011-08-04 13:50:17 +0000120 if (false) {
121 SkPaint paint;
122 paint.setAntiAlias(true);
123 paint.setTextSize(50);
124 paint.setTypeface(SkTypeface::CreateFromName("Arial Unicode MS", SkTypeface::kNormal));
125 SkSafeUnref(paint.getTypeface());
126 char buffer[10];
127 size_t len = SkUTF8_FromUnichar(0x8500, buffer);
128 canvas->drawText(buffer, len, 40, 40, paint);
129 return;
130 }
reed@google.com0e0c94c2011-08-04 18:11:01 +0000131 if (false) {
reed@google.com87fac4a2011-08-04 13:50:17 +0000132 SkPaint paint;
133 paint.setAntiAlias(true);
rmistry@google.comae933ce2012-08-23 18:19:56 +0000134
reed@google.com87fac4a2011-08-04 13:50:17 +0000135 SkRect r0 = { 0, 0, 10.5f, 20 };
136 SkRect r1 = { 10.5f, 10, 20, 30 };
137 paint.setColor(SK_ColorRED);
138 canvas->drawRect(r0, paint);
139 paint.setColor(SK_ColorBLUE);
140 canvas->drawRect(r1, paint);
141 return;
142 }
143
bsalomon@google.com271cffc2011-05-20 14:13:56 +0000144 const struct {
145 SkXfermode::Mode fMode;
146 const char* fLabel;
147 } gModes[] = {
148 { SkXfermode::kClear_Mode, "Clear" },
149 { SkXfermode::kSrc_Mode, "Src" },
150 { SkXfermode::kDst_Mode, "Dst" },
151 { SkXfermode::kSrcOver_Mode, "SrcOver" },
152 { SkXfermode::kDstOver_Mode, "DstOver" },
153 { SkXfermode::kSrcIn_Mode, "SrcIn" },
154 { SkXfermode::kDstIn_Mode, "DstIn" },
155 { SkXfermode::kSrcOut_Mode, "SrcOut" },
156 { SkXfermode::kDstOut_Mode, "DstOut" },
157 { SkXfermode::kSrcATop_Mode, "SrcATop" },
158 { SkXfermode::kDstATop_Mode, "DstATop" },
159 { SkXfermode::kXor_Mode, "Xor" },
160
161 { SkXfermode::kPlus_Mode, "Plus" },
162 /*{ SkXfermode::kMultiply_Mode, "Multiply" },
163 { SkXfermode::kScreen_Mode, "Screen" },
164 { SkXfermode::kOverlay_Mode, "Overlay" },
165 { SkXfermode::kDarken_Mode, "Darken" },
166 { SkXfermode::kLighten_Mode, "Lighten" },
167 { SkXfermode::kColorDodge_Mode, "ColorDodge" },
168 { SkXfermode::kColorBurn_Mode, "ColorBurn" },
169 { SkXfermode::kHardLight_Mode, "HardLight" },
170 { SkXfermode::kSoftLight_Mode, "SoftLight" },
171 { SkXfermode::kDifference_Mode, "Difference" },
172 { SkXfermode::kExclusion_Mode, "Exclusion" },*/
173 };
174
175 const SkScalar w = SkIntToScalar(W);
176 const SkScalar h = SkIntToScalar(H);
177 SkShader* s = SkShader::CreateBitmapShader(fBG,
178 SkShader::kRepeat_TileMode,
179 SkShader::kRepeat_TileMode);
180 SkMatrix m;
181 m.setScale(SkIntToScalar(6), SkIntToScalar(6));
182 s->setLocalMatrix(m);
183
184 SkPaint labelP;
185 labelP.setAntiAlias(true);
186 labelP.setLCDRenderText(true);
187 labelP.setTextAlign(SkPaint::kCenter_Align);
188 setNamedTypeface(&labelP, "Menlo Regular");
189
190 const int W = 5;
191
192 SkScalar x0 = 0;
193 for (int twice = 0; twice < 2; twice++) {
194 SkScalar x = x0, y = 0;
195 for (size_t i = 0; i < SK_ARRAY_COUNT(gModes); i++) {
196 SkXfermode* mode = SkXfermode::Create(gModes[i].fMode);
197 SkAutoUnref aur(mode);
198 SkRect r;
199 r.set(x, y, x+w, y+h);
200
201 SkPaint p;
202 p.setStyle(SkPaint::kFill_Style);
203 p.setShader(s);
204 canvas->drawRect(r, p);
205
206 canvas->saveLayer(&r, NULL, SkCanvas::kARGB_ClipLayer_SaveFlag);
207 draw_mode(canvas, mode, twice ? 0x88 : 0xFF, r.fLeft, r.fTop);
208 canvas->restore();
209
210 r.inset(-SK_ScalarHalf, -SK_ScalarHalf);
211 p.setStyle(SkPaint::kStroke_Style);
212 p.setShader(NULL);
213 canvas->drawRect(r, p);
214
215 canvas->drawText(gModes[i].fLabel, strlen(gModes[i].fLabel),
216 x + w/2, y - labelP.getTextSize()/2, labelP);
217 x += w + SkIntToScalar(10);
218 if ((i % W) == W - 1) {
219 x = x0;
220 y += h + SkIntToScalar(30);
221 }
222 }
223 x0 += SkIntToScalar(400);
224 }
225 s->unref();
226 }
227
228private:
229 typedef SampleView INHERITED;
230};
231
232//////////////////////////////////////////////////////////////////////////////
233
234static SkView* MyFactory() { return new XfermodesBlurView; }
235static SkViewRegister reg(MyFactory);