1 /*
2 * Copyright 2018 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 "SkOpPE.h"
9 #include "SkStrokeRec.h"
10 #include "SkReadBuffer.h"
11 #include "SkWriteBuffer.h"
12
Make(sk_sp<SkPathEffect> one,sk_sp<SkPathEffect> two,SkPathOp op)13 sk_sp<SkPathEffect> SkMergePathEffect::Make(sk_sp<SkPathEffect> one, sk_sp<SkPathEffect> two,
14 SkPathOp op) {
15 return sk_sp<SkPathEffect>(new SkOpPE(std::move(one), std::move(two), op));
16 }
17
SkOpPE(sk_sp<SkPathEffect> one,sk_sp<SkPathEffect> two,SkPathOp op)18 SkOpPE::SkOpPE(sk_sp<SkPathEffect> one, sk_sp<SkPathEffect> two, SkPathOp op)
19 : fOne(std::move(one)), fTwo(std::move(two)), fOp(op) {}
20
onFilterPath(SkPath * dst,const SkPath & src,SkStrokeRec * rec,const SkRect * cull) const21 bool SkOpPE::onFilterPath(SkPath* dst, const SkPath& src, SkStrokeRec* rec,
22 const SkRect* cull) const {
23 SkPath one, two;
24 if (fOne) {
25 if (!fOne->filterPath(&one, src, rec, cull)) {
26 return false;
27 }
28 } else {
29 one = src;
30 }
31 if (fTwo) {
32 if (!fTwo->filterPath(&two, src, rec, cull)) {
33 return false;
34 }
35 } else {
36 two = src;
37 }
38 return Op(one, two, fOp, dst);
39 }
40
flatten(SkWriteBuffer & buffer) const41 void SkOpPE::flatten(SkWriteBuffer& buffer) const {
42 buffer.writeFlattenable(fOne.get());
43 buffer.writeFlattenable(fTwo.get());
44 buffer.write32(fOp);
45 }
46
CreateProc(SkReadBuffer & buffer)47 sk_sp<SkFlattenable> SkOpPE::CreateProc(SkReadBuffer& buffer) {
48 auto one = buffer.readPathEffect();
49 auto two = buffer.readPathEffect();
50 SkPathOp op = buffer.read32LE(kReverseDifference_SkPathOp);
51 return buffer.isValid() ? SkMergePathEffect::Make(std::move(one), std::move(two), op) : nullptr;
52 }
53
54 //////////////////////////////////////////////////////////////////////////////////////////////////
55
MakeTranslate(SkScalar dx,SkScalar dy)56 sk_sp<SkPathEffect> SkMatrixPathEffect::MakeTranslate(SkScalar dx, SkScalar dy) {
57 if (!SkScalarsAreFinite(dx, dy)) {
58 return nullptr;
59 }
60 return sk_sp<SkPathEffect>(new SkMatrixPE(SkMatrix::MakeTrans(dx, dy)));
61 }
62
Make(const SkMatrix & matrix)63 sk_sp<SkPathEffect> SkMatrixPathEffect::Make(const SkMatrix& matrix) {
64 if (!matrix.isFinite()) {
65 return nullptr;
66 }
67 return sk_sp<SkPathEffect>(new SkMatrixPE(matrix));
68 }
69
SkMatrixPE(const SkMatrix & matrix)70 SkMatrixPE::SkMatrixPE(const SkMatrix& matrix) : fMatrix(matrix) {
71 SkASSERT(matrix.isFinite());
72 }
73
onFilterPath(SkPath * dst,const SkPath & src,SkStrokeRec *,const SkRect *) const74 bool SkMatrixPE::onFilterPath(SkPath* dst, const SkPath& src, SkStrokeRec*, const SkRect*) const {
75 src.transform(fMatrix, dst);
76 return true;
77 }
78
flatten(SkWriteBuffer & buffer) const79 void SkMatrixPE::flatten(SkWriteBuffer& buffer) const {
80 buffer.writeMatrix(fMatrix);
81 }
82
CreateProc(SkReadBuffer & buffer)83 sk_sp<SkFlattenable> SkMatrixPE::CreateProc(SkReadBuffer& buffer) {
84 SkMatrix mx;
85 buffer.readMatrix(&mx);
86 return buffer.isValid() ? SkMatrixPathEffect::Make(mx) : nullptr;
87 }
88
89 //////////////////////////////////////////////////////////////////////////////////////////////////
90
Make(SkScalar width,SkPaint::Join join,SkPaint::Cap cap,SkScalar miter)91 sk_sp<SkPathEffect> SkStrokePathEffect::Make(SkScalar width, SkPaint::Join join, SkPaint::Cap cap,
92 SkScalar miter) {
93 if (!SkScalarsAreFinite(width, miter) || width < 0 || miter < 0) {
94 return nullptr;
95 }
96 return sk_sp<SkPathEffect>(new SkStrokePE(width, join, cap, miter));
97 }
98
SkStrokePE(SkScalar width,SkPaint::Join join,SkPaint::Cap cap,SkScalar miter)99 SkStrokePE::SkStrokePE(SkScalar width, SkPaint::Join join, SkPaint::Cap cap, SkScalar miter)
100 : fWidth(width), fMiter(miter), fJoin(join), fCap(cap) {}
101
onFilterPath(SkPath * dst,const SkPath & src,SkStrokeRec *,const SkRect *) const102 bool SkStrokePE::onFilterPath(SkPath* dst, const SkPath& src, SkStrokeRec*, const SkRect*) const {
103 SkStrokeRec rec(SkStrokeRec::kFill_InitStyle);
104 rec.setStrokeStyle(fWidth);
105 rec.setStrokeParams(fCap, fJoin, fMiter);
106 return rec.applyToPath(dst, src);
107 }
108
flatten(SkWriteBuffer & buffer) const109 void SkStrokePE::flatten(SkWriteBuffer& buffer) const {
110 buffer.writeScalar(fWidth);
111 buffer.writeScalar(fMiter);
112 buffer.write32(fJoin);
113 buffer.write32(fCap);
114 }
115
CreateProc(SkReadBuffer & buffer)116 sk_sp<SkFlattenable> SkStrokePE::CreateProc(SkReadBuffer& buffer) {
117 SkScalar width = buffer.readScalar();
118 SkScalar miter = buffer.readScalar();
119 SkPaint::Join join = buffer.read32LE(SkPaint::kLast_Join);
120 SkPaint::Cap cap = buffer.read32LE(SkPaint::kLast_Cap);
121 return buffer.isValid() ? SkStrokePathEffect::Make(width, join, cap, miter) : nullptr;
122 }
123
124
125