OLD | NEW |
1 /* | 1 /* |
2 * Copyright 2006 The Android Open Source Project | 2 * Copyright 2006 The Android Open Source Project |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license that can be | 4 * Use of this source code is governed by a BSD-style license that can be |
5 * found in the LICENSE file. | 5 * found in the LICENSE file. |
6 */ | 6 */ |
7 | 7 |
8 #include "SkPaint.h" | 8 #include "SkPaint.h" |
9 #include "SkAnnotation.h" | 9 #include "SkAnnotation.h" |
10 #include "SkAutoKern.h" | 10 #include "SkAutoKern.h" |
(...skipping 16 matching lines...) Expand all Loading... |
27 #include "SkScalerContext.h" | 27 #include "SkScalerContext.h" |
28 #include "SkShader.h" | 28 #include "SkShader.h" |
29 #include "SkStringUtils.h" | 29 #include "SkStringUtils.h" |
30 #include "SkStroke.h" | 30 #include "SkStroke.h" |
31 #include "SkTextFormatParams.h" | 31 #include "SkTextFormatParams.h" |
32 #include "SkTextToPathIter.h" | 32 #include "SkTextToPathIter.h" |
33 #include "SkTLazy.h" | 33 #include "SkTLazy.h" |
34 #include "SkTypeface.h" | 34 #include "SkTypeface.h" |
35 #include "SkXfermode.h" | 35 #include "SkXfermode.h" |
36 | 36 |
37 enum { | |
38 kColor_DirtyBit = 1 << 0, | |
39 kTextSize_DirtyBit = 1 << 1, | |
40 kTextScaleX_DirtyBit = 1 << 2, | |
41 kTextSkewX_DirtyBit = 1 << 3, | |
42 kStrokeWidth_DirtyBit = 1 << 4, | |
43 kStrokeMiter_DirtyBit = 1 << 5, | |
44 | |
45 kPOD_DirtyBitMask = 63, | |
46 | |
47 kPathEffect_DirtyBit = 1 << 6, | |
48 kShader_DirtyBit = 1 << 7, | |
49 kXfermode_DirtyBit = 1 << 8, | |
50 kMaskFilter_DirtyBit = 1 << 9, | |
51 kColorFilter_DirtyBit = 1 << 10, | |
52 kRasterizer_DirtyBit = 1 << 11, | |
53 kLooper_DirtyBit = 1 << 12, | |
54 kImageFilter_DirtyBit = 1 << 13, | |
55 kTypeface_DirtyBit = 1 << 14, | |
56 kAnnotation_DirtyBit = 1 << 15, | |
57 }; | |
58 | |
59 // define this to get a printf for out-of-range parameter in setters | 37 // define this to get a printf for out-of-range parameter in setters |
60 // e.g. setTextSize(-1) | 38 // e.g. setTextSize(-1) |
61 //#define SK_REPORT_API_RANGE_CHECK | 39 //#define SK_REPORT_API_RANGE_CHECK |
62 | 40 |
63 #ifdef SK_BUILD_FOR_ANDROID | 41 #ifdef SK_BUILD_FOR_ANDROID |
64 #define GEN_ID_INC fGenerationID++ | 42 #define GEN_ID_INC fGenerationID++ |
65 #define GEN_ID_INC_EVAL(expression) if (expression) { fGenerationID++; } | 43 #define GEN_ID_INC_EVAL(expression) if (expression) { fGenerationID++; } |
66 #else | 44 #else |
67 #define GEN_ID_INC | 45 #define GEN_ID_INC |
68 #define GEN_ID_INC_EVAL(expression) | 46 #define GEN_ID_INC_EVAL(expression) |
(...skipping 21 matching lines...) Expand all Loading... |
90 // Zero all bitfields, then set some non-zero defaults. | 68 // Zero all bitfields, then set some non-zero defaults. |
91 fBitfieldsUInt = 0; | 69 fBitfieldsUInt = 0; |
92 fBitfields.fFlags = SkPaintDefaults_Flags; | 70 fBitfields.fFlags = SkPaintDefaults_Flags; |
93 fBitfields.fCapType = kDefault_Cap; | 71 fBitfields.fCapType = kDefault_Cap; |
94 fBitfields.fJoinType = kDefault_Join; | 72 fBitfields.fJoinType = kDefault_Join; |
95 fBitfields.fTextAlign = kLeft_Align; | 73 fBitfields.fTextAlign = kLeft_Align; |
96 fBitfields.fStyle = kFill_Style; | 74 fBitfields.fStyle = kFill_Style; |
97 fBitfields.fTextEncoding = kUTF8_TextEncoding; | 75 fBitfields.fTextEncoding = kUTF8_TextEncoding; |
98 fBitfields.fHinting = SkPaintDefaults_Hinting; | 76 fBitfields.fHinting = SkPaintDefaults_Hinting; |
99 | 77 |
100 fDirtyBits = 0; | |
101 #ifdef SK_BUILD_FOR_ANDROID | 78 #ifdef SK_BUILD_FOR_ANDROID |
102 fGenerationID = 0; | 79 fGenerationID = 0; |
103 #endif | 80 #endif |
104 } | 81 } |
105 | 82 |
106 SkPaint::SkPaint(const SkPaint& src) { | 83 SkPaint::SkPaint(const SkPaint& src) { |
107 #define COPY(field) field = src.field | 84 #define COPY(field) field = src.field |
108 #define REF_COPY(field) field = SkSafeRef(src.field) | 85 #define REF_COPY(field) field = SkSafeRef(src.field) |
109 | 86 |
110 REF_COPY(fTypeface); | 87 REF_COPY(fTypeface); |
111 REF_COPY(fPathEffect); | 88 REF_COPY(fPathEffect); |
112 REF_COPY(fShader); | 89 REF_COPY(fShader); |
113 REF_COPY(fXfermode); | 90 REF_COPY(fXfermode); |
114 REF_COPY(fMaskFilter); | 91 REF_COPY(fMaskFilter); |
115 REF_COPY(fColorFilter); | 92 REF_COPY(fColorFilter); |
116 REF_COPY(fRasterizer); | 93 REF_COPY(fRasterizer); |
117 REF_COPY(fLooper); | 94 REF_COPY(fLooper); |
118 REF_COPY(fImageFilter); | 95 REF_COPY(fImageFilter); |
119 REF_COPY(fAnnotation); | 96 REF_COPY(fAnnotation); |
120 | 97 |
121 COPY(fTextSize); | 98 COPY(fTextSize); |
122 COPY(fTextScaleX); | 99 COPY(fTextScaleX); |
123 COPY(fTextSkewX); | 100 COPY(fTextSkewX); |
124 COPY(fColor); | 101 COPY(fColor); |
125 COPY(fWidth); | 102 COPY(fWidth); |
126 COPY(fMiterLimit); | 103 COPY(fMiterLimit); |
127 COPY(fBitfields); | 104 COPY(fBitfields); |
128 COPY(fDirtyBits); | |
129 | 105 |
130 #ifdef SK_BUILD_FOR_ANDROID | 106 #ifdef SK_BUILD_FOR_ANDROID |
131 COPY(fGenerationID); | 107 COPY(fGenerationID); |
132 #endif | 108 #endif |
133 | 109 |
134 #undef COPY | 110 #undef COPY |
135 #undef REF_COPY | 111 #undef REF_COPY |
136 } | 112 } |
137 | 113 |
138 SkPaint::~SkPaint() { | 114 SkPaint::~SkPaint() { |
(...skipping 30 matching lines...) Expand all Loading... |
169 REF_COPY(fImageFilter); | 145 REF_COPY(fImageFilter); |
170 REF_COPY(fAnnotation); | 146 REF_COPY(fAnnotation); |
171 | 147 |
172 COPY(fTextSize); | 148 COPY(fTextSize); |
173 COPY(fTextScaleX); | 149 COPY(fTextScaleX); |
174 COPY(fTextSkewX); | 150 COPY(fTextSkewX); |
175 COPY(fColor); | 151 COPY(fColor); |
176 COPY(fWidth); | 152 COPY(fWidth); |
177 COPY(fMiterLimit); | 153 COPY(fMiterLimit); |
178 COPY(fBitfields); | 154 COPY(fBitfields); |
179 COPY(fDirtyBits); | |
180 | |
181 #ifdef SK_BUILD_FOR_ANDROID | 155 #ifdef SK_BUILD_FOR_ANDROID |
182 ++fGenerationID; | 156 ++fGenerationID; |
183 #endif | 157 #endif |
184 | 158 |
185 return *this; | 159 return *this; |
186 | 160 |
187 #undef COPY | 161 #undef COPY |
188 #undef REF_COPY | 162 #undef REF_COPY |
189 } | 163 } |
190 | 164 |
191 bool operator==(const SkPaint& a, const SkPaint& b) { | 165 bool operator==(const SkPaint& a, const SkPaint& b) { |
192 #define EQUAL(field) (a.field == b.field) | 166 #define EQUAL(field) (a.field == b.field) |
193 // Don't check fGenerationID, which can be different for logically equal pai
nts. | 167 // Don't check fGenerationID, which can be different for logically equal pai
nts. |
194 // fDirtyBits is a very quick check for non-equality, so check it first. | 168 return EQUAL(fTypeface) |
195 return EQUAL(fDirtyBits) | |
196 && EQUAL(fTypeface) | |
197 && EQUAL(fPathEffect) | 169 && EQUAL(fPathEffect) |
198 && EQUAL(fShader) | 170 && EQUAL(fShader) |
199 && EQUAL(fXfermode) | 171 && EQUAL(fXfermode) |
200 && EQUAL(fMaskFilter) | 172 && EQUAL(fMaskFilter) |
201 && EQUAL(fColorFilter) | 173 && EQUAL(fColorFilter) |
202 && EQUAL(fRasterizer) | 174 && EQUAL(fRasterizer) |
203 && EQUAL(fLooper) | 175 && EQUAL(fLooper) |
204 && EQUAL(fImageFilter) | 176 && EQUAL(fImageFilter) |
205 && EQUAL(fAnnotation) | 177 && EQUAL(fAnnotation) |
206 && EQUAL(fTextSize) | 178 && EQUAL(fTextSize) |
(...skipping 103 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
310 } else { | 282 } else { |
311 #ifdef SK_REPORT_API_RANGE_CHECK | 283 #ifdef SK_REPORT_API_RANGE_CHECK |
312 SkDebugf("SkPaint::setStyle(%d) out of range\n", style); | 284 SkDebugf("SkPaint::setStyle(%d) out of range\n", style); |
313 #endif | 285 #endif |
314 } | 286 } |
315 } | 287 } |
316 | 288 |
317 void SkPaint::setColor(SkColor color) { | 289 void SkPaint::setColor(SkColor color) { |
318 GEN_ID_INC_EVAL(color != fColor); | 290 GEN_ID_INC_EVAL(color != fColor); |
319 fColor = color; | 291 fColor = color; |
320 fDirtyBits = SkSetClearMask(fDirtyBits, color != SK_ColorBLACK, kColor_Dirty
Bit); | |
321 } | 292 } |
322 | 293 |
323 void SkPaint::setAlpha(U8CPU a) { | 294 void SkPaint::setAlpha(U8CPU a) { |
324 this->setColor(SkColorSetARGB(a, SkColorGetR(fColor), | 295 this->setColor(SkColorSetARGB(a, SkColorGetR(fColor), |
325 SkColorGetG(fColor), SkColorGetB(fColor))); | 296 SkColorGetG(fColor), SkColorGetB(fColor))); |
326 } | 297 } |
327 | 298 |
328 void SkPaint::setARGB(U8CPU a, U8CPU r, U8CPU g, U8CPU b) { | 299 void SkPaint::setARGB(U8CPU a, U8CPU r, U8CPU g, U8CPU b) { |
329 this->setColor(SkColorSetARGB(a, r, g, b)); | 300 this->setColor(SkColorSetARGB(a, r, g, b)); |
330 } | 301 } |
331 | 302 |
332 void SkPaint::setStrokeWidth(SkScalar width) { | 303 void SkPaint::setStrokeWidth(SkScalar width) { |
333 if (width >= 0) { | 304 if (width >= 0) { |
334 GEN_ID_INC_EVAL(width != fWidth); | 305 GEN_ID_INC_EVAL(width != fWidth); |
335 fWidth = width; | 306 fWidth = width; |
336 fDirtyBits = SkSetClearMask(fDirtyBits, width != 0, kStrokeWidth_DirtyBi
t); | |
337 } else { | 307 } else { |
338 #ifdef SK_REPORT_API_RANGE_CHECK | 308 #ifdef SK_REPORT_API_RANGE_CHECK |
339 SkDebugf("SkPaint::setStrokeWidth() called with negative value\n"); | 309 SkDebugf("SkPaint::setStrokeWidth() called with negative value\n"); |
340 #endif | 310 #endif |
341 } | 311 } |
342 } | 312 } |
343 | 313 |
344 void SkPaint::setStrokeMiter(SkScalar limit) { | 314 void SkPaint::setStrokeMiter(SkScalar limit) { |
345 if (limit >= 0) { | 315 if (limit >= 0) { |
346 GEN_ID_INC_EVAL(limit != fMiterLimit); | 316 GEN_ID_INC_EVAL(limit != fMiterLimit); |
347 fMiterLimit = limit; | 317 fMiterLimit = limit; |
348 fDirtyBits = SkSetClearMask(fDirtyBits, | |
349 limit != SkPaintDefaults_MiterLimit, | |
350 kStrokeMiter_DirtyBit); | |
351 } else { | 318 } else { |
352 #ifdef SK_REPORT_API_RANGE_CHECK | 319 #ifdef SK_REPORT_API_RANGE_CHECK |
353 SkDebugf("SkPaint::setStrokeMiter() called with negative value\n"); | 320 SkDebugf("SkPaint::setStrokeMiter() called with negative value\n"); |
354 #endif | 321 #endif |
355 } | 322 } |
356 } | 323 } |
357 | 324 |
358 void SkPaint::setStrokeCap(Cap ct) { | 325 void SkPaint::setStrokeCap(Cap ct) { |
359 if ((unsigned)ct < kCapCount) { | 326 if ((unsigned)ct < kCapCount) { |
360 GEN_ID_INC_EVAL((unsigned)ct != fBitfields.fCapType); | 327 GEN_ID_INC_EVAL((unsigned)ct != fBitfields.fCapType); |
(...skipping 26 matching lines...) Expand all Loading... |
387 #ifdef SK_REPORT_API_RANGE_CHECK | 354 #ifdef SK_REPORT_API_RANGE_CHECK |
388 SkDebugf("SkPaint::setTextAlign(%d) out of range\n", align); | 355 SkDebugf("SkPaint::setTextAlign(%d) out of range\n", align); |
389 #endif | 356 #endif |
390 } | 357 } |
391 } | 358 } |
392 | 359 |
393 void SkPaint::setTextSize(SkScalar ts) { | 360 void SkPaint::setTextSize(SkScalar ts) { |
394 if (ts >= 0) { | 361 if (ts >= 0) { |
395 GEN_ID_INC_EVAL(ts != fTextSize); | 362 GEN_ID_INC_EVAL(ts != fTextSize); |
396 fTextSize = ts; | 363 fTextSize = ts; |
397 fDirtyBits = SkSetClearMask(fDirtyBits, ts != SkPaintDefaults_TextSize,
kTextSize_DirtyBit); | |
398 } else { | 364 } else { |
399 #ifdef SK_REPORT_API_RANGE_CHECK | 365 #ifdef SK_REPORT_API_RANGE_CHECK |
400 SkDebugf("SkPaint::setTextSize() called with negative value\n"); | 366 SkDebugf("SkPaint::setTextSize() called with negative value\n"); |
401 #endif | 367 #endif |
402 } | 368 } |
403 } | 369 } |
404 | 370 |
405 void SkPaint::setTextScaleX(SkScalar scaleX) { | 371 void SkPaint::setTextScaleX(SkScalar scaleX) { |
406 GEN_ID_INC_EVAL(scaleX != fTextScaleX); | 372 GEN_ID_INC_EVAL(scaleX != fTextScaleX); |
407 fTextScaleX = scaleX; | 373 fTextScaleX = scaleX; |
408 fDirtyBits = SkSetClearMask(fDirtyBits, scaleX != SK_Scalar1, kTextScaleX_Di
rtyBit); | |
409 } | 374 } |
410 | 375 |
411 void SkPaint::setTextSkewX(SkScalar skewX) { | 376 void SkPaint::setTextSkewX(SkScalar skewX) { |
412 GEN_ID_INC_EVAL(skewX != fTextSkewX); | 377 GEN_ID_INC_EVAL(skewX != fTextSkewX); |
413 fTextSkewX = skewX; | 378 fTextSkewX = skewX; |
414 fDirtyBits = SkSetClearMask(fDirtyBits, skewX != 0, kTextSkewX_DirtyBit); | |
415 } | 379 } |
416 | 380 |
417 void SkPaint::setTextEncoding(TextEncoding encoding) { | 381 void SkPaint::setTextEncoding(TextEncoding encoding) { |
418 if ((unsigned)encoding <= kGlyphID_TextEncoding) { | 382 if ((unsigned)encoding <= kGlyphID_TextEncoding) { |
419 GEN_ID_INC_EVAL((unsigned)encoding != fBitfields.fTextEncoding); | 383 GEN_ID_INC_EVAL((unsigned)encoding != fBitfields.fTextEncoding); |
420 fBitfields.fTextEncoding = encoding; | 384 fBitfields.fTextEncoding = encoding; |
421 } else { | 385 } else { |
422 #ifdef SK_REPORT_API_RANGE_CHECK | 386 #ifdef SK_REPORT_API_RANGE_CHECK |
423 SkDebugf("SkPaint::setTextEncoding(%d) out of range\n", encoding); | 387 SkDebugf("SkPaint::setTextEncoding(%d) out of range\n", encoding); |
424 #endif | 388 #endif |
425 } | 389 } |
426 } | 390 } |
427 | 391 |
428 /////////////////////////////////////////////////////////////////////////////// | 392 /////////////////////////////////////////////////////////////////////////////// |
429 | 393 |
430 SkTypeface* SkPaint::setTypeface(SkTypeface* font) { | 394 SkTypeface* SkPaint::setTypeface(SkTypeface* font) { |
431 SkRefCnt_SafeAssign(fTypeface, font); | 395 SkRefCnt_SafeAssign(fTypeface, font); |
432 GEN_ID_INC; | 396 GEN_ID_INC; |
433 fDirtyBits = SkSetClearMask(fDirtyBits, font != NULL, kTypeface_DirtyBit); | |
434 return font; | 397 return font; |
435 } | 398 } |
436 | 399 |
437 SkRasterizer* SkPaint::setRasterizer(SkRasterizer* r) { | 400 SkRasterizer* SkPaint::setRasterizer(SkRasterizer* r) { |
438 SkRefCnt_SafeAssign(fRasterizer, r); | 401 SkRefCnt_SafeAssign(fRasterizer, r); |
439 GEN_ID_INC; | 402 GEN_ID_INC; |
440 fDirtyBits = SkSetClearMask(fDirtyBits, r != NULL, kRasterizer_DirtyBit); | |
441 return r; | 403 return r; |
442 } | 404 } |
443 | 405 |
444 SkDrawLooper* SkPaint::setLooper(SkDrawLooper* looper) { | 406 SkDrawLooper* SkPaint::setLooper(SkDrawLooper* looper) { |
445 SkRefCnt_SafeAssign(fLooper, looper); | 407 SkRefCnt_SafeAssign(fLooper, looper); |
446 GEN_ID_INC; | 408 GEN_ID_INC; |
447 fDirtyBits = SkSetClearMask(fDirtyBits, looper != NULL, kLooper_DirtyBit); | |
448 return looper; | 409 return looper; |
449 } | 410 } |
450 | 411 |
451 SkImageFilter* SkPaint::setImageFilter(SkImageFilter* imageFilter) { | 412 SkImageFilter* SkPaint::setImageFilter(SkImageFilter* imageFilter) { |
452 SkRefCnt_SafeAssign(fImageFilter, imageFilter); | 413 SkRefCnt_SafeAssign(fImageFilter, imageFilter); |
453 GEN_ID_INC; | 414 GEN_ID_INC; |
454 fDirtyBits = SkSetClearMask(fDirtyBits, imageFilter != NULL, kImageFilter_Di
rtyBit); | |
455 return imageFilter; | 415 return imageFilter; |
456 } | 416 } |
457 | 417 |
458 SkAnnotation* SkPaint::setAnnotation(SkAnnotation* annotation) { | 418 SkAnnotation* SkPaint::setAnnotation(SkAnnotation* annotation) { |
459 SkRefCnt_SafeAssign(fAnnotation, annotation); | 419 SkRefCnt_SafeAssign(fAnnotation, annotation); |
460 GEN_ID_INC; | 420 GEN_ID_INC; |
461 fDirtyBits = SkSetClearMask(fDirtyBits, annotation != NULL, kAnnotation_Dirt
yBit); | |
462 return annotation; | 421 return annotation; |
463 } | 422 } |
464 | 423 |
465 /////////////////////////////////////////////////////////////////////////////// | 424 /////////////////////////////////////////////////////////////////////////////// |
466 | 425 |
467 static SkScalar mag2(SkScalar x, SkScalar y) { | 426 static SkScalar mag2(SkScalar x, SkScalar y) { |
468 return x * x + y * y; | 427 return x * x + y * y; |
469 } | 428 } |
470 | 429 |
471 static bool tooBig(const SkMatrix& m, SkScalar ma2max) { | 430 static bool tooBig(const SkMatrix& m, SkScalar ma2max) { |
(...skipping 1726 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2198 buffer.readString(&tag); | 2157 buffer.readString(&tag); |
2199 buffer.readBool(); | 2158 buffer.readBool(); |
2200 } | 2159 } |
2201 } | 2160 } |
2202 | 2161 |
2203 /////////////////////////////////////////////////////////////////////////////// | 2162 /////////////////////////////////////////////////////////////////////////////// |
2204 | 2163 |
2205 SkShader* SkPaint::setShader(SkShader* shader) { | 2164 SkShader* SkPaint::setShader(SkShader* shader) { |
2206 GEN_ID_INC_EVAL(shader != fShader); | 2165 GEN_ID_INC_EVAL(shader != fShader); |
2207 SkRefCnt_SafeAssign(fShader, shader); | 2166 SkRefCnt_SafeAssign(fShader, shader); |
2208 fDirtyBits = SkSetClearMask(fDirtyBits, shader != NULL, kShader_DirtyBit); | |
2209 return shader; | 2167 return shader; |
2210 } | 2168 } |
2211 | 2169 |
2212 SkColorFilter* SkPaint::setColorFilter(SkColorFilter* filter) { | 2170 SkColorFilter* SkPaint::setColorFilter(SkColorFilter* filter) { |
2213 GEN_ID_INC_EVAL(filter != fColorFilter); | 2171 GEN_ID_INC_EVAL(filter != fColorFilter); |
2214 SkRefCnt_SafeAssign(fColorFilter, filter); | 2172 SkRefCnt_SafeAssign(fColorFilter, filter); |
2215 fDirtyBits = SkSetClearMask(fDirtyBits, filter != NULL, kColorFilter_DirtyBi
t); | |
2216 return filter; | 2173 return filter; |
2217 } | 2174 } |
2218 | 2175 |
2219 SkXfermode* SkPaint::setXfermode(SkXfermode* mode) { | 2176 SkXfermode* SkPaint::setXfermode(SkXfermode* mode) { |
2220 GEN_ID_INC_EVAL(mode != fXfermode); | 2177 GEN_ID_INC_EVAL(mode != fXfermode); |
2221 SkRefCnt_SafeAssign(fXfermode, mode); | 2178 SkRefCnt_SafeAssign(fXfermode, mode); |
2222 fDirtyBits = SkSetClearMask(fDirtyBits, mode != NULL, kXfermode_DirtyBit); | |
2223 return mode; | 2179 return mode; |
2224 } | 2180 } |
2225 | 2181 |
2226 SkXfermode* SkPaint::setXfermodeMode(SkXfermode::Mode mode) { | 2182 SkXfermode* SkPaint::setXfermodeMode(SkXfermode::Mode mode) { |
2227 SkSafeUnref(fXfermode); | 2183 SkSafeUnref(fXfermode); |
2228 fXfermode = SkXfermode::Create(mode); | 2184 fXfermode = SkXfermode::Create(mode); |
2229 GEN_ID_INC; | 2185 GEN_ID_INC; |
2230 fDirtyBits = SkSetClearMask(fDirtyBits, fXfermode != NULL, kXfermode_DirtyBi
t); | |
2231 return fXfermode; | 2186 return fXfermode; |
2232 } | 2187 } |
2233 | 2188 |
2234 SkPathEffect* SkPaint::setPathEffect(SkPathEffect* effect) { | 2189 SkPathEffect* SkPaint::setPathEffect(SkPathEffect* effect) { |
2235 GEN_ID_INC_EVAL(effect != fPathEffect); | 2190 GEN_ID_INC_EVAL(effect != fPathEffect); |
2236 SkRefCnt_SafeAssign(fPathEffect, effect); | 2191 SkRefCnt_SafeAssign(fPathEffect, effect); |
2237 fDirtyBits = SkSetClearMask(fDirtyBits, effect != NULL, kPathEffect_DirtyBit
); | |
2238 return effect; | 2192 return effect; |
2239 } | 2193 } |
2240 | 2194 |
2241 SkMaskFilter* SkPaint::setMaskFilter(SkMaskFilter* filter) { | 2195 SkMaskFilter* SkPaint::setMaskFilter(SkMaskFilter* filter) { |
2242 GEN_ID_INC_EVAL(filter != fMaskFilter); | 2196 GEN_ID_INC_EVAL(filter != fMaskFilter); |
2243 SkRefCnt_SafeAssign(fMaskFilter, filter); | 2197 SkRefCnt_SafeAssign(fMaskFilter, filter); |
2244 fDirtyBits = SkSetClearMask(fDirtyBits, filter != NULL, kMaskFilter_DirtyBit
); | |
2245 return filter; | 2198 return filter; |
2246 } | 2199 } |
2247 | 2200 |
2248 /////////////////////////////////////////////////////////////////////////////// | 2201 /////////////////////////////////////////////////////////////////////////////// |
2249 | 2202 |
2250 bool SkPaint::getFillPath(const SkPath& src, SkPath* dst, | 2203 bool SkPaint::getFillPath(const SkPath& src, SkPath* dst, |
2251 const SkRect* cullRect) const { | 2204 const SkRect* cullRect) const { |
2252 SkStrokeRec rec(*this); | 2205 SkStrokeRec rec(*this); |
2253 | 2206 |
2254 const SkPath* srcPtr = &src; | 2207 const SkPath* srcPtr = &src; |
(...skipping 349 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2604 return 0 == this->getAlpha(); | 2557 return 0 == this->getAlpha(); |
2605 case SkXfermode::kDst_Mode: | 2558 case SkXfermode::kDst_Mode: |
2606 return true; | 2559 return true; |
2607 default: | 2560 default: |
2608 break; | 2561 break; |
2609 } | 2562 } |
2610 } | 2563 } |
2611 return false; | 2564 return false; |
2612 } | 2565 } |
2613 | 2566 |
2614 inline static unsigned popcount(uint8_t x) { | |
2615 // As in Hacker's delight, adapted for just 8 bits. | |
2616 x = (x & 0x55) + ((x >> 1) & 0x55); // a b c d w x y z -> a+b c+d w+x y+z | |
2617 x = (x & 0x33) + ((x >> 2) & 0x33); // a+b c+d w+x y+z -> a+b+c+d w+x+y+z | |
2618 x = (x & 0x0F) + ((x >> 4) & 0x0F); // a+b+c+d w+x+y+z -> a+b+c+d+w+x+y+z | |
2619 return x; | |
2620 } | |
2621 | |
2622 void SkPaint::FlatteningTraits::Flatten(SkWriteBuffer& buffer, const SkPaint& pa
int) { | |
2623 const uint32_t dirty = paint.fDirtyBits; | |
2624 | |
2625 // Each of the low 7 dirty bits corresponds to a 4-byte flat value, | |
2626 // plus one for the dirty bits and one for the bitfields | |
2627 const size_t flatBytes = 4 * (popcount(dirty & kPOD_DirtyBitMask) + 2); | |
2628 SkASSERT(flatBytes <= 32); | |
2629 uint32_t* u32 = buffer.reserve(flatBytes); | |
2630 *u32++ = dirty; | |
2631 *u32++ = paint.fBitfieldsUInt; | |
2632 if (0 == dirty) { | |
2633 return; | |
2634 } | |
2635 | |
2636 #define F(dst, field) if (dirty & k##field##_DirtyBit) *dst++ = paint.get##field
() | |
2637 F(u32, Color); | |
2638 SkScalar* f32 = reinterpret_cast<SkScalar*>(u32); | |
2639 F(f32, TextSize); | |
2640 F(f32, TextScaleX); | |
2641 F(f32, TextSkewX); | |
2642 F(f32, StrokeWidth); | |
2643 F(f32, StrokeMiter); | |
2644 #undef F | |
2645 #define F(field) if (dirty & k##field##_DirtyBit) buffer.writeFlattenable(paint.
get##field()) | |
2646 F(PathEffect); | |
2647 F(Shader); | |
2648 F(Xfermode); | |
2649 F(MaskFilter); | |
2650 F(ColorFilter); | |
2651 F(Rasterizer); | |
2652 F(Looper); | |
2653 F(ImageFilter); | |
2654 #undef F | |
2655 if (dirty & kTypeface_DirtyBit) buffer.writeTypeface(paint.getTypeface()); | |
2656 if (dirty & kAnnotation_DirtyBit) paint.getAnnotation()->writeToBuffer(buffe
r); | |
2657 } | |
2658 | |
2659 void SkPaint::FlatteningTraits::Unflatten(SkReadBuffer& buffer, SkPaint* paint)
{ | |
2660 const uint32_t dirty = buffer.readUInt(); | |
2661 paint->fBitfieldsUInt = buffer.readUInt(); | |
2662 if (dirty == 0) { | |
2663 return; | |
2664 } | |
2665 #define F(field, reader) if (dirty & k##field##_DirtyBit) paint->set##field(buff
er.reader()) | |
2666 // Same function, except it unrefs the object newly set on the paint: | |
2667 #define F_UNREF(field, reader) \ | |
2668 if (dirty & k##field##_DirtyBit) \ | |
2669 paint->set##field(buffer.reader())->unref() | |
2670 | |
2671 F(Color, readUInt); | |
2672 F(TextSize, readScalar); | |
2673 F(TextScaleX, readScalar); | |
2674 F(TextSkewX, readScalar); | |
2675 F(StrokeWidth, readScalar); | |
2676 F(StrokeMiter, readScalar); | |
2677 F_UNREF(PathEffect, readPathEffect); | |
2678 F_UNREF(Shader, readShader); | |
2679 F_UNREF(Xfermode, readXfermode); | |
2680 F_UNREF(MaskFilter, readMaskFilter); | |
2681 F_UNREF(ColorFilter, readColorFilter); | |
2682 F_UNREF(Rasterizer, readRasterizer); | |
2683 F_UNREF(Looper, readDrawLooper); | |
2684 F_UNREF(ImageFilter, readImageFilter); | |
2685 F(Typeface, readTypeface); | |
2686 #undef F | |
2687 #undef F_UNREF | |
2688 if (dirty & kAnnotation_DirtyBit) { | |
2689 paint->setAnnotation(SkAnnotation::Create(buffer))->unref(); | |
2690 } | |
2691 SkASSERT(dirty == paint->fDirtyBits); | |
2692 } | |
OLD | NEW |