| 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 "SkBuffer.h" | 8 #include "SkBuffer.h" |
| 9 #include "SkErrorInternals.h" | 9 #include "SkErrorInternals.h" |
| 10 #include "SkGeometry.h" | 10 #include "SkGeometry.h" |
| (...skipping 822 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 833 if (fLastMoveToIndex >= 0) { | 833 if (fLastMoveToIndex >= 0) { |
| 834 fLastMoveToIndex = ~fLastMoveToIndex; | 834 fLastMoveToIndex = ~fLastMoveToIndex; |
| 835 } | 835 } |
| 836 #else | 836 #else |
| 837 fLastMoveToIndex ^= ~fLastMoveToIndex >> (8 * sizeof(fLastMoveToIndex) - 1); | 837 fLastMoveToIndex ^= ~fLastMoveToIndex >> (8 * sizeof(fLastMoveToIndex) - 1); |
| 838 #endif | 838 #endif |
| 839 } | 839 } |
| 840 | 840 |
| 841 /////////////////////////////////////////////////////////////////////////////// | 841 /////////////////////////////////////////////////////////////////////////////// |
| 842 | 842 |
| 843 namespace { |
| 844 |
| 845 template <unsigned N> |
| 846 class PointIterator { |
| 847 public: |
| 848 PointIterator(SkPath::Direction dir, unsigned startIndex) |
| 849 : fCurrent(startIndex % N) |
| 850 , fAdvance(dir == SkPath::kCW_Direction ? 1 : N - 1) { } |
| 851 |
| 852 const SkPoint& current() const { |
| 853 SkASSERT(fCurrent < N); |
| 854 return fPts[fCurrent]; |
| 855 } |
| 856 |
| 857 const SkPoint& next() { |
| 858 fCurrent = (fCurrent + fAdvance) % N; |
| 859 return this->current(); |
| 860 } |
| 861 |
| 862 protected: |
| 863 SkPoint fPts[N]; |
| 864 |
| 865 private: |
| 866 unsigned fCurrent; |
| 867 unsigned fAdvance; |
| 868 }; |
| 869 |
| 870 class RectPointIterator : public PointIterator<4> { |
| 871 public: |
| 872 RectPointIterator(const SkRect& rect, SkPath::Direction dir, unsigned startI
ndex) |
| 873 : PointIterator(dir, startIndex) { |
| 874 |
| 875 fPts[0] = SkPoint::Make(rect.fLeft, rect.fTop); |
| 876 fPts[1] = SkPoint::Make(rect.fRight, rect.fTop); |
| 877 fPts[2] = SkPoint::Make(rect.fRight, rect.fBottom); |
| 878 fPts[3] = SkPoint::Make(rect.fLeft, rect.fBottom); |
| 879 } |
| 880 }; |
| 881 |
| 882 class OvalPointIterator : public PointIterator<4> { |
| 883 public: |
| 884 OvalPointIterator(const SkRect& oval, SkPath::Direction dir, unsigned startI
ndex) |
| 885 : PointIterator(dir, startIndex) { |
| 886 |
| 887 const SkScalar cx = oval.centerX(); |
| 888 const SkScalar cy = oval.centerY(); |
| 889 |
| 890 fPts[0] = SkPoint::Make(cx, oval.fTop); |
| 891 fPts[1] = SkPoint::Make(oval.fRight, cy); |
| 892 fPts[2] = SkPoint::Make(cx, oval.fBottom); |
| 893 fPts[3] = SkPoint::Make(oval.fLeft, cy); |
| 894 } |
| 895 }; |
| 896 |
| 897 class RRectPointIterator : public PointIterator<8> { |
| 898 public: |
| 899 RRectPointIterator(const SkRRect& rrect, SkPath::Direction dir, unsigned sta
rtIndex) |
| 900 : PointIterator(dir, startIndex) { |
| 901 |
| 902 const SkRect& bounds = rrect.getBounds(); |
| 903 const SkScalar L = bounds.fLeft; |
| 904 const SkScalar T = bounds.fTop; |
| 905 const SkScalar R = bounds.fRight; |
| 906 const SkScalar B = bounds.fBottom; |
| 907 |
| 908 fPts[0] = SkPoint::Make(L + rrect.radii(SkRRect::kUpperLeft_Corner).fX,
T); |
| 909 fPts[1] = SkPoint::Make(R - rrect.radii(SkRRect::kUpperRight_Corner).fX,
T); |
| 910 fPts[2] = SkPoint::Make(R, T + rrect.radii(SkRRect::kUpperRight_Corner).
fY); |
| 911 fPts[3] = SkPoint::Make(R, B - rrect.radii(SkRRect::kLowerRight_Corner).
fY); |
| 912 fPts[4] = SkPoint::Make(R - rrect.radii(SkRRect::kLowerRight_Corner).fX,
B); |
| 913 fPts[5] = SkPoint::Make(L + rrect.radii(SkRRect::kLowerLeft_Corner).fX,
B); |
| 914 fPts[6] = SkPoint::Make(L, B - rrect.radii(SkRRect::kLowerLeft_Corner).f
Y); |
| 915 fPts[7] = SkPoint::Make(L, T + rrect.radii(SkRRect::kUpperLeft_Corner).f
Y); |
| 916 } |
| 917 }; |
| 918 |
| 919 } // anonymous namespace |
| 920 |
| 843 static void assert_known_direction(int dir) { | 921 static void assert_known_direction(int dir) { |
| 844 SkASSERT(SkPath::kCW_Direction == dir || SkPath::kCCW_Direction == dir); | 922 SkASSERT(SkPath::kCW_Direction == dir || SkPath::kCCW_Direction == dir); |
| 845 } | 923 } |
| 846 | 924 |
| 847 void SkPath::addRect(const SkRect& rect, Direction dir) { | 925 void SkPath::addRect(const SkRect& rect, Direction dir) { |
| 848 this->addRect(rect.fLeft, rect.fTop, rect.fRight, rect.fBottom, dir); | 926 this->addRect(rect, dir, 0); |
| 849 } | 927 } |
| 850 | 928 |
| 851 void SkPath::addRect(SkScalar left, SkScalar top, SkScalar right, | 929 void SkPath::addRect(SkScalar left, SkScalar top, SkScalar right, |
| 852 SkScalar bottom, Direction dir) { | 930 SkScalar bottom, Direction dir) { |
| 931 this->addRect(SkRect::MakeLTRB(left, top, right, bottom), dir, 0); |
| 932 } |
| 933 |
| 934 void SkPath::addRect(const SkRect &rect, Direction dir, unsigned startIndex) { |
| 853 assert_known_direction(dir); | 935 assert_known_direction(dir); |
| 854 fFirstDirection = this->hasOnlyMoveTos() ? | 936 fFirstDirection = this->hasOnlyMoveTos() ? |
| 855 (SkPathPriv::FirstDirection)dir : SkPathPriv::kUnknown_F
irstDirection; | 937 (SkPathPriv::FirstDirection)dir : SkPathPriv::kUnknown_FirstDirection; |
| 856 SkAutoDisableDirectionCheck addc(this); | 938 SkAutoDisableDirectionCheck addc(this); |
| 939 SkAutoPathBoundsUpdate apbu(this, rect); |
| 857 | 940 |
| 858 SkAutoPathBoundsUpdate apbu(this, left, top, right, bottom); | 941 SkDEBUGCODE(int initialVerbCount = this->countVerbs()); |
| 859 | 942 |
| 860 this->incReserve(5); | 943 const int kVerbs = 5; // moveTo + 3x lineTo + close |
| 944 this->incReserve(kVerbs); |
| 861 | 945 |
| 862 this->moveTo(left, top); | 946 RectPointIterator iter(rect, dir, startIndex); |
| 863 if (dir == kCCW_Direction) { | 947 |
| 864 this->lineTo(left, bottom); | 948 this->moveTo(iter.current()); |
| 865 this->lineTo(right, bottom); | 949 this->lineTo(iter.next()); |
| 866 this->lineTo(right, top); | 950 this->lineTo(iter.next()); |
| 867 } else { | 951 this->lineTo(iter.next()); |
| 868 this->lineTo(right, top); | |
| 869 this->lineTo(right, bottom); | |
| 870 this->lineTo(left, bottom); | |
| 871 } | |
| 872 this->close(); | 952 this->close(); |
| 953 |
| 954 SkASSERT(this->countVerbs() == initialVerbCount + kVerbs); |
| 873 } | 955 } |
| 874 | 956 |
| 875 void SkPath::addPoly(const SkPoint pts[], int count, bool close) { | 957 void SkPath::addPoly(const SkPoint pts[], int count, bool close) { |
| 876 SkDEBUGCODE(this->validate();) | 958 SkDEBUGCODE(this->validate();) |
| 877 if (count <= 0) { | 959 if (count <= 0) { |
| 878 return; | 960 return; |
| 879 } | 961 } |
| 880 | 962 |
| 881 fLastMoveToIndex = fPathRef->countPoints(); | 963 fLastMoveToIndex = fPathRef->countPoints(); |
| 882 | 964 |
| (...skipping 89 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 972 } | 1054 } |
| 973 | 1055 |
| 974 void SkPath::addRoundRect(const SkRect& rect, const SkScalar radii[], | 1056 void SkPath::addRoundRect(const SkRect& rect, const SkScalar radii[], |
| 975 Direction dir) { | 1057 Direction dir) { |
| 976 SkRRect rrect; | 1058 SkRRect rrect; |
| 977 rrect.setRectRadii(rect, (const SkVector*) radii); | 1059 rrect.setRectRadii(rect, (const SkVector*) radii); |
| 978 this->addRRect(rrect, dir); | 1060 this->addRRect(rrect, dir); |
| 979 } | 1061 } |
| 980 | 1062 |
| 981 void SkPath::addRRect(const SkRRect& rrect, Direction dir) { | 1063 void SkPath::addRRect(const SkRRect& rrect, Direction dir) { |
| 982 assert_known_direction(dir); | 1064 // legacy start indices: 6 (CW) and 7(CCW) |
| 1065 this->addRRect(rrect, dir, dir == kCW_Direction ? 6 : 7); |
| 1066 } |
| 983 | 1067 |
| 984 if (rrect.isEmpty()) { | 1068 void SkPath::addRRect(const SkRRect &rrect, Direction dir, unsigned startIndex)
{ |
| 985 return; | 1069 assert_known_direction(dir); |
| 986 } | |
| 987 | 1070 |
| 988 const SkRect& bounds = rrect.getBounds(); | 1071 if (rrect.isEmpty()) { |
| 1072 return; |
| 1073 } |
| 989 | 1074 |
| 990 if (rrect.isRect()) { | 1075 const SkRect& bounds = rrect.getBounds(); |
| 991 this->addRect(bounds, dir); | |
| 992 } else if (rrect.isOval()) { | |
| 993 this->addOval(bounds, dir); | |
| 994 } else { | |
| 995 fFirstDirection = this->hasOnlyMoveTos() ? | |
| 996 (SkPathPriv::FirstDirection)dir : SkPathPriv::kUnkno
wn_FirstDirection; | |
| 997 | 1076 |
| 998 SkAutoPathBoundsUpdate apbu(this, bounds); | 1077 if (rrect.isRect()) { |
| 999 SkAutoDisableDirectionCheck addc(this); | 1078 // degenerate(rect) => radii points are collapsing |
| 1079 this->addRect(bounds, dir, (startIndex + 1) / 2); |
| 1080 } else if (rrect.isOval()) { |
| 1081 // degenerate(oval) => line points are collapsing |
| 1082 this->addOval(bounds, dir, startIndex / 2); |
| 1083 } else { |
| 1084 fFirstDirection = this->hasOnlyMoveTos() ? |
| 1085 (SkPathPriv::FirstDirection)dir : SkPathPriv::kU
nknown_FirstDirection; |
| 1000 | 1086 |
| 1001 const SkScalar L = bounds.fLeft; | 1087 SkAutoPathBoundsUpdate apbu(this, bounds); |
| 1002 const SkScalar T = bounds.fTop; | 1088 SkAutoDisableDirectionCheck addc(this); |
| 1003 const SkScalar R = bounds.fRight; | |
| 1004 const SkScalar B = bounds.fBottom; | |
| 1005 const SkScalar W = SK_ScalarRoot2Over2; | |
| 1006 | 1089 |
| 1007 this->incReserve(13); | 1090 // we start with a conic on odd indices when moving CW vs. even indi
ces when moving CCW |
| 1008 if (kCW_Direction == dir) { | 1091 const bool startsWithConic = ((startIndex & 1) == (dir == kCW_Direct
ion)); |
| 1009 this->moveTo(L, B - rrect.fRadii[SkRRect::kLowerLeft_Corner].fY); | 1092 const SkScalar weight = SK_ScalarRoot2Over2; |
| 1010 | 1093 |
| 1011 this->lineTo(L, T + rrect.fRadii[SkRRect::kUpperLeft_Corner].fY); | 1094 SkDEBUGCODE(int initialVerbCount = this->countVerbs()); |
| 1012 this->conicTo(L, T, L + rrect.fRadii[SkRRect::kUpperLeft_Corner].fX,
T, W); | 1095 const int kVerbs = startsWithConic |
| 1096 ? 9 // moveTo + 4x conicTo + 3x lineTo + close |
| 1097 : 10; // moveTo + 4x lineTo + 4x conicTo + close |
| 1098 this->incReserve(kVerbs); |
| 1013 | 1099 |
| 1014 this->lineTo(R - rrect.fRadii[SkRRect::kUpperRight_Corner].fX, T); | 1100 RRectPointIterator rrectIter(rrect, dir, startIndex); |
| 1015 this->conicTo(R, T, R, T + rrect.fRadii[SkRRect::kUpperRight_Corner]
.fY, W); | 1101 // Corner iterator indices follow the collapsed radii model, |
| 1102 // adjusted such that the start pt is "behind" the radii start pt. |
| 1103 const unsigned rectStartIndex = startIndex / 2 + (dir == kCW_Directi
on ? 0 : 1); |
| 1104 RectPointIterator rectIter(bounds, dir, rectStartIndex); |
| 1016 | 1105 |
| 1017 this->lineTo(R, B - rrect.fRadii[SkRRect::kLowerRight_Corner].fY); | 1106 this->moveTo(rrectIter.current()); |
| 1018 this->conicTo(R, B, R - rrect.fRadii[SkRRect::kLowerRight_Corner].fX
, B, W); | 1107 if (startsWithConic) { |
| 1108 for (unsigned i = 0; i < 3; ++i) { |
| 1109 this->conicTo(rectIter.next(), rrectIter.next(), weight); |
| 1110 this->lineTo(rrectIter.next()); |
| 1111 } |
| 1112 this->conicTo(rectIter.next(), rrectIter.next(), weight); |
| 1113 // final lineTo handled by close(). |
| 1114 } else { |
| 1115 for (unsigned i = 0; i < 4; ++i) { |
| 1116 this->lineTo(rrectIter.next()); |
| 1117 this->conicTo(rectIter.next(), rrectIter.next(), weight); |
| 1118 } |
| 1119 } |
| 1120 this->close(); |
| 1019 | 1121 |
| 1020 this->lineTo(L + rrect.fRadii[SkRRect::kLowerLeft_Corner].fX, B); | 1122 SkASSERT(this->countVerbs() == initialVerbCount + kVerbs); |
| 1021 this->conicTo(L, B, L, B - rrect.fRadii[SkRRect::kLowerLeft_Corner].
fY, W); | 1123 } |
| 1022 } else { | |
| 1023 this->moveTo(L, T + rrect.fRadii[SkRRect::kUpperLeft_Corner].fY); | |
| 1024 | 1124 |
| 1025 this->lineTo(L, B - rrect.fRadii[SkRRect::kLowerLeft_Corner].fY); | 1125 SkDEBUGCODE(fPathRef->validate();) |
| 1026 this->conicTo(L, B, L + rrect.fRadii[SkRRect::kLowerLeft_Corner].fX,
B, W); | |
| 1027 | |
| 1028 this->lineTo(R - rrect.fRadii[SkRRect::kLowerRight_Corner].fX, B); | |
| 1029 this->conicTo(R, B, R, B - rrect.fRadii[SkRRect::kLowerRight_Corner]
.fY, W); | |
| 1030 | |
| 1031 this->lineTo(R, T + rrect.fRadii[SkRRect::kUpperRight_Corner].fY); | |
| 1032 this->conicTo(R, T, R - rrect.fRadii[SkRRect::kUpperRight_Corner].fX
, T, W); | |
| 1033 | |
| 1034 this->lineTo(L + rrect.fRadii[SkRRect::kUpperLeft_Corner].fX, T); | |
| 1035 this->conicTo(L, T, L, T + rrect.fRadii[SkRRect::kUpperLeft_Corner].
fY, W); | |
| 1036 } | |
| 1037 this->close(); | |
| 1038 } | |
| 1039 SkDEBUGCODE(fPathRef->validate();) | |
| 1040 } | 1126 } |
| 1041 | 1127 |
| 1042 bool SkPath::hasOnlyMoveTos() const { | 1128 bool SkPath::hasOnlyMoveTos() const { |
| 1043 int count = fPathRef->countVerbs(); | 1129 int count = fPathRef->countVerbs(); |
| 1044 const uint8_t* verbs = const_cast<const SkPathRef*>(fPathRef.get())->verbsMe
mBegin(); | 1130 const uint8_t* verbs = const_cast<const SkPathRef*>(fPathRef.get())->verbsMe
mBegin(); |
| 1045 for (int i = 0; i < count; ++i) { | 1131 for (int i = 0; i < count; ++i) { |
| 1046 if (*verbs == kLine_Verb || | 1132 if (*verbs == kLine_Verb || |
| 1047 *verbs == kQuad_Verb || | 1133 *verbs == kQuad_Verb || |
| 1048 *verbs == kConic_Verb || | 1134 *verbs == kConic_Verb || |
| 1049 *verbs == kCubic_Verb) { | 1135 *verbs == kCubic_Verb) { |
| (...skipping 15 matching lines...) Expand all Loading... |
| 1065 SkScalarToDouble(rx), SkScalarToDouble(ry) )
; | 1151 SkScalarToDouble(rx), SkScalarToDouble(ry) )
; |
| 1066 return; | 1152 return; |
| 1067 } | 1153 } |
| 1068 | 1154 |
| 1069 SkRRect rrect; | 1155 SkRRect rrect; |
| 1070 rrect.setRectXY(rect, rx, ry); | 1156 rrect.setRectXY(rect, rx, ry); |
| 1071 this->addRRect(rrect, dir); | 1157 this->addRRect(rrect, dir); |
| 1072 } | 1158 } |
| 1073 | 1159 |
| 1074 void SkPath::addOval(const SkRect& oval, Direction dir) { | 1160 void SkPath::addOval(const SkRect& oval, Direction dir) { |
| 1161 // legacy start index: 1 |
| 1162 this->addOval(oval, dir, 1); |
| 1163 } |
| 1164 |
| 1165 void SkPath::addOval(const SkRect &oval, Direction dir, unsigned startPointIndex
) { |
| 1075 assert_known_direction(dir); | 1166 assert_known_direction(dir); |
| 1076 | 1167 |
| 1077 /* If addOval() is called after previous moveTo(), | 1168 /* If addOval() is called after previous moveTo(), |
| 1078 this path is still marked as an oval. This is used to | 1169 this path is still marked as an oval. This is used to |
| 1079 fit into WebKit's calling sequences. | 1170 fit into WebKit's calling sequences. |
| 1080 We can't simply check isEmpty() in this case, as additional | 1171 We can't simply check isEmpty() in this case, as additional |
| 1081 moveTo() would mark the path non empty. | 1172 moveTo() would mark the path non empty. |
| 1082 */ | 1173 */ |
| 1083 bool isOval = hasOnlyMoveTos(); | 1174 bool isOval = hasOnlyMoveTos(); |
| 1084 if (isOval) { | 1175 if (isOval) { |
| 1085 fFirstDirection = (SkPathPriv::FirstDirection)dir; | 1176 fFirstDirection = (SkPathPriv::FirstDirection)dir; |
| 1086 } else { | 1177 } else { |
| 1087 fFirstDirection = SkPathPriv::kUnknown_FirstDirection; | 1178 fFirstDirection = SkPathPriv::kUnknown_FirstDirection; |
| 1088 } | 1179 } |
| 1089 | 1180 |
| 1090 SkAutoDisableDirectionCheck addc(this); | 1181 SkAutoDisableDirectionCheck addc(this); |
| 1091 | |
| 1092 SkAutoPathBoundsUpdate apbu(this, oval); | 1182 SkAutoPathBoundsUpdate apbu(this, oval); |
| 1093 | 1183 |
| 1094 const SkScalar L = oval.fLeft; | 1184 SkDEBUGCODE(int initialVerbCount = this->countVerbs()); |
| 1095 const SkScalar T = oval.fTop; | 1185 const int kVerbs = 6; // moveTo + 4x conicTo + close |
| 1096 const SkScalar R = oval.fRight; | 1186 this->incReserve(kVerbs); |
| 1097 const SkScalar B = oval.fBottom; | 1187 |
| 1098 const SkScalar cx = oval.centerX(); | 1188 OvalPointIterator ovalIter(oval, dir, startPointIndex); |
| 1099 const SkScalar cy = oval.centerY(); | 1189 // The corner iterator pts are tracking "behind" the oval/radii pts. |
| 1190 RectPointIterator rectIter(oval, dir, startPointIndex + (dir == kCW_Directio
n ? 0 : 1)); |
| 1100 const SkScalar weight = SK_ScalarRoot2Over2; | 1191 const SkScalar weight = SK_ScalarRoot2Over2; |
| 1101 | 1192 |
| 1102 this->incReserve(9); // move + 4 conics | 1193 this->moveTo(ovalIter.current()); |
| 1103 this->moveTo(R, cy); | 1194 for (unsigned i = 0; i < 4; ++i) { |
| 1104 if (dir == kCCW_Direction) { | 1195 this->conicTo(rectIter.next(), ovalIter.next(), weight); |
| 1105 this->conicTo(R, T, cx, T, weight); | |
| 1106 this->conicTo(L, T, L, cy, weight); | |
| 1107 this->conicTo(L, B, cx, B, weight); | |
| 1108 this->conicTo(R, B, R, cy, weight); | |
| 1109 } else { | |
| 1110 this->conicTo(R, B, cx, B, weight); | |
| 1111 this->conicTo(L, B, L, cy, weight); | |
| 1112 this->conicTo(L, T, cx, T, weight); | |
| 1113 this->conicTo(R, T, R, cy, weight); | |
| 1114 } | 1196 } |
| 1115 this->close(); | 1197 this->close(); |
| 1116 | 1198 |
| 1199 SkASSERT(this->countVerbs() == initialVerbCount + kVerbs); |
| 1200 |
| 1117 SkPathRef::Editor ed(&fPathRef); | 1201 SkPathRef::Editor ed(&fPathRef); |
| 1118 | 1202 |
| 1119 ed.setIsOval(isOval); | 1203 ed.setIsOval(isOval); |
| 1120 } | 1204 } |
| 1121 | 1205 |
| 1122 void SkPath::addCircle(SkScalar x, SkScalar y, SkScalar r, Direction dir) { | 1206 void SkPath::addCircle(SkScalar x, SkScalar y, SkScalar r, Direction dir) { |
| 1123 if (r > 0) { | 1207 if (r > 0) { |
| 1124 SkRect rect; | 1208 this->addOval(SkRect::MakeLTRB(x - r, y - r, x + r, y + r), dir); |
| 1125 rect.set(x - r, y - r, x + r, y + r); | |
| 1126 this->addOval(rect, dir); | |
| 1127 } | 1209 } |
| 1128 } | 1210 } |
| 1129 | 1211 |
| 1130 void SkPath::arcTo(const SkRect& oval, SkScalar startAngle, SkScalar sweepAngle, | 1212 void SkPath::arcTo(const SkRect& oval, SkScalar startAngle, SkScalar sweepAngle, |
| 1131 bool forceMoveTo) { | 1213 bool forceMoveTo) { |
| 1132 if (oval.width() < 0 || oval.height() < 0) { | 1214 if (oval.width() < 0 || oval.height() < 0) { |
| 1133 return; | 1215 return; |
| 1134 } | 1216 } |
| 1135 | 1217 |
| 1136 if (fPathRef->countVerbs() == 0) { | 1218 if (fPathRef->countVerbs() == 0) { |
| (...skipping 1676 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2813 switch (this->getFillType()) { | 2895 switch (this->getFillType()) { |
| 2814 case SkPath::kEvenOdd_FillType: | 2896 case SkPath::kEvenOdd_FillType: |
| 2815 case SkPath::kInverseEvenOdd_FillType: | 2897 case SkPath::kInverseEvenOdd_FillType: |
| 2816 w &= 1; | 2898 w &= 1; |
| 2817 break; | 2899 break; |
| 2818 default: | 2900 default: |
| 2819 break; | 2901 break; |
| 2820 } | 2902 } |
| 2821 return SkToBool(w); | 2903 return SkToBool(w); |
| 2822 } | 2904 } |
| OLD | NEW |