Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(81)

Side by Side Diff: src/core/SkPath.cpp

Issue 105083003: Move segment mask from SkPath to SkPathRef (Closed) Base URL: http://skia.googlecode.com/svn/trunk/
Patch Set: switched growForRepeatedVerb to return conic weight pointer Created 7 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « include/core/SkPathRef.h ('k') | src/core/SkPathRef.cpp » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 1
2 /* 2 /*
3 * Copyright 2006 The Android Open Source Project 3 * Copyright 2006 The Android Open Source Project
4 * 4 *
5 * Use of this source code is governed by a BSD-style license that can be 5 * Use of this source code is governed by a BSD-style license that can be
6 * found in the LICENSE file. 6 * found in the LICENSE file.
7 */ 7 */
8 8
9 9
10 #include "SkBuffer.h" 10 #include "SkBuffer.h"
11 #include "SkErrorInternals.h" 11 #include "SkErrorInternals.h"
12 #include "SkMath.h" 12 #include "SkMath.h"
13 #include "SkPath.h" 13 #include "SkPath.h"
14 #include "SkPathRef.h" 14 #include "SkPathRef.h"
15 #include "SkRRect.h" 15 #include "SkRRect.h"
16 #include "SkThread.h" 16 #include "SkThread.h"
17 17
18 // This value is just made-up for now. When count is 4, calling memset was much
19 // slower than just writing the loop. This seems odd, and hopefully in the
20 // future this we appear to have been a fluke...
21 #define MIN_COUNT_FOR_MEMSET_TO_BE_FAST 16
22
23 //////////////////////////////////////////////////////////////////////////// 18 ////////////////////////////////////////////////////////////////////////////
24 19
25 /** 20 /**
26 * Path.bounds is defined to be the bounds of all the control points. 21 * Path.bounds is defined to be the bounds of all the control points.
27 * If we called bounds.join(r) we would skip r if r was empty, which breaks 22 * If we called bounds.join(r) we would skip r if r was empty, which breaks
28 * our promise. Hence we have a custom joiner that doesn't look at emptiness 23 * our promise. Hence we have a custom joiner that doesn't look at emptiness
29 */ 24 */
30 static void joinNoEmptyChecks(SkRect* dst, const SkRect& src) { 25 static void joinNoEmptyChecks(SkRect* dst, const SkRect& src) {
31 dst->fLeft = SkMinScalar(dst->fLeft, src.fLeft); 26 dst->fLeft = SkMinScalar(dst->fLeft, src.fLeft);
32 dst->fTop = SkMinScalar(dst->fTop, src.fTop); 27 dst->fTop = SkMinScalar(dst->fTop, src.fTop);
(...skipping 103 matching lines...) Expand 10 before | Expand all | Expand 10 after
136 , fSourcePath(NULL) 131 , fSourcePath(NULL)
137 #endif 132 #endif
138 { 133 {
139 this->resetFields(); 134 this->resetFields();
140 } 135 }
141 136
142 void SkPath::resetFields() { 137 void SkPath::resetFields() {
143 //fPathRef is assumed to have been emptied by the caller. 138 //fPathRef is assumed to have been emptied by the caller.
144 fLastMoveToIndex = INITIAL_LASTMOVETOINDEX_VALUE; 139 fLastMoveToIndex = INITIAL_LASTMOVETOINDEX_VALUE;
145 fFillType = kWinding_FillType; 140 fFillType = kWinding_FillType;
146 fSegmentMask = 0;
147 fConvexity = kUnknown_Convexity; 141 fConvexity = kUnknown_Convexity;
148 fDirection = kUnknown_Direction; 142 fDirection = kUnknown_Direction;
149 143
150 // We don't touch Android's fSourcePath. It's used to track texture garbage collection, so we 144 // We don't touch Android's fSourcePath. It's used to track texture garbage collection, so we
151 // don't want to muck with it if it's been set to something non-NULL. 145 // don't want to muck with it if it's been set to something non-NULL.
152 } 146 }
153 147
154 SkPath::SkPath(const SkPath& that) 148 SkPath::SkPath(const SkPath& that)
155 : fPathRef(SkRef(that.fPathRef.get())) { 149 : fPathRef(SkRef(that.fPathRef.get())) {
156 this->copyFields(that); 150 this->copyFields(that);
(...skipping 18 matching lines...) Expand all
175 #endif 169 #endif
176 } 170 }
177 SkDEBUGCODE(this->validate();) 171 SkDEBUGCODE(this->validate();)
178 return *this; 172 return *this;
179 } 173 }
180 174
181 void SkPath::copyFields(const SkPath& that) { 175 void SkPath::copyFields(const SkPath& that) {
182 //fPathRef is assumed to have been set by the caller. 176 //fPathRef is assumed to have been set by the caller.
183 fLastMoveToIndex = that.fLastMoveToIndex; 177 fLastMoveToIndex = that.fLastMoveToIndex;
184 fFillType = that.fFillType; 178 fFillType = that.fFillType;
185 fSegmentMask = that.fSegmentMask;
186 fConvexity = that.fConvexity; 179 fConvexity = that.fConvexity;
187 fDirection = that.fDirection; 180 fDirection = that.fDirection;
188 } 181 }
189 182
190 bool operator==(const SkPath& a, const SkPath& b) { 183 bool operator==(const SkPath& a, const SkPath& b) {
191 // note: don't need to look at isConvex or bounds, since just comparing the 184 // note: don't need to look at isConvex or bounds, since just comparing the
192 // raw data is sufficient. 185 // raw data is sufficient.
193
194 // We explicitly check fSegmentMask as a quick-reject. We could skip it,
195 // since it is only a cache of info in the fVerbs, but its a fast way to
196 // notice a difference
197
198 return &a == &b || 186 return &a == &b ||
199 (a.fFillType == b.fFillType && a.fSegmentMask == b.fSegmentMask && 187 (a.fFillType == b.fFillType && *a.fPathRef.get() == *b.fPathRef.get());
200 *a.fPathRef.get() == *b.fPathRef.get());
201 } 188 }
202 189
203 void SkPath::swap(SkPath& that) { 190 void SkPath::swap(SkPath& that) {
204 SkASSERT(&that != NULL); 191 SkASSERT(&that != NULL);
205 192
206 if (this != &that) { 193 if (this != &that) {
207 fPathRef.swap(&that.fPathRef); 194 fPathRef.swap(&that.fPathRef);
208 SkTSwap<int>(fLastMoveToIndex, that.fLastMoveToIndex); 195 SkTSwap<int>(fLastMoveToIndex, that.fLastMoveToIndex);
209 SkTSwap<uint8_t>(fFillType, that.fFillType); 196 SkTSwap<uint8_t>(fFillType, that.fFillType);
210 SkTSwap<uint8_t>(fSegmentMask, that.fSegmentMask);
211 SkTSwap<uint8_t>(fConvexity, that.fConvexity); 197 SkTSwap<uint8_t>(fConvexity, that.fConvexity);
212 SkTSwap<uint8_t>(fDirection, that.fDirection); 198 SkTSwap<uint8_t>(fDirection, that.fDirection);
213 #ifdef SK_BUILD_FOR_ANDROID 199 #ifdef SK_BUILD_FOR_ANDROID
214 SkTSwap<const SkPath*>(fSourcePath, that.fSourcePath); 200 SkTSwap<const SkPath*>(fSourcePath, that.fSourcePath);
215 #endif 201 #endif
216 } 202 }
217 } 203 }
218 204
219 static inline bool check_edge_against_rect(const SkPoint& p0, 205 static inline bool check_edge_against_rect(const SkPoint& p0,
220 const SkPoint& p1, 206 const SkPoint& p1,
(...skipping 446 matching lines...) Expand 10 before | Expand all | Expand 10 after
667 } 653 }
668 } 654 }
669 655
670 void SkPath::lineTo(SkScalar x, SkScalar y) { 656 void SkPath::lineTo(SkScalar x, SkScalar y) {
671 SkDEBUGCODE(this->validate();) 657 SkDEBUGCODE(this->validate();)
672 658
673 this->injectMoveToIfNeeded(); 659 this->injectMoveToIfNeeded();
674 660
675 SkPathRef::Editor ed(&fPathRef); 661 SkPathRef::Editor ed(&fPathRef);
676 ed.growForVerb(kLine_Verb)->set(x, y); 662 ed.growForVerb(kLine_Verb)->set(x, y);
677 fSegmentMask |= kLine_SegmentMask;
678 663
679 DIRTY_AFTER_EDIT; 664 DIRTY_AFTER_EDIT;
680 } 665 }
681 666
682 void SkPath::rLineTo(SkScalar x, SkScalar y) { 667 void SkPath::rLineTo(SkScalar x, SkScalar y) {
683 this->injectMoveToIfNeeded(); // This can change the result of this->getLas tPt(). 668 this->injectMoveToIfNeeded(); // This can change the result of this->getLas tPt().
684 SkPoint pt; 669 SkPoint pt;
685 this->getLastPt(&pt); 670 this->getLastPt(&pt);
686 this->lineTo(pt.fX + x, pt.fY + y); 671 this->lineTo(pt.fX + x, pt.fY + y);
687 } 672 }
688 673
689 void SkPath::quadTo(SkScalar x1, SkScalar y1, SkScalar x2, SkScalar y2) { 674 void SkPath::quadTo(SkScalar x1, SkScalar y1, SkScalar x2, SkScalar y2) {
690 SkDEBUGCODE(this->validate();) 675 SkDEBUGCODE(this->validate();)
691 676
692 this->injectMoveToIfNeeded(); 677 this->injectMoveToIfNeeded();
693 678
694 SkPathRef::Editor ed(&fPathRef); 679 SkPathRef::Editor ed(&fPathRef);
695 SkPoint* pts = ed.growForVerb(kQuad_Verb); 680 SkPoint* pts = ed.growForVerb(kQuad_Verb);
696 pts[0].set(x1, y1); 681 pts[0].set(x1, y1);
697 pts[1].set(x2, y2); 682 pts[1].set(x2, y2);
698 fSegmentMask |= kQuad_SegmentMask;
699 683
700 DIRTY_AFTER_EDIT; 684 DIRTY_AFTER_EDIT;
701 } 685 }
702 686
703 void SkPath::rQuadTo(SkScalar x1, SkScalar y1, SkScalar x2, SkScalar y2) { 687 void SkPath::rQuadTo(SkScalar x1, SkScalar y1, SkScalar x2, SkScalar y2) {
704 this->injectMoveToIfNeeded(); // This can change the result of this->getLas tPt(). 688 this->injectMoveToIfNeeded(); // This can change the result of this->getLas tPt().
705 SkPoint pt; 689 SkPoint pt;
706 this->getLastPt(&pt); 690 this->getLastPt(&pt);
707 this->quadTo(pt.fX + x1, pt.fY + y1, pt.fX + x2, pt.fY + y2); 691 this->quadTo(pt.fX + x1, pt.fY + y1, pt.fX + x2, pt.fY + y2);
708 } 692 }
709 693
710 void SkPath::conicTo(SkScalar x1, SkScalar y1, SkScalar x2, SkScalar y2, 694 void SkPath::conicTo(SkScalar x1, SkScalar y1, SkScalar x2, SkScalar y2,
711 SkScalar w) { 695 SkScalar w) {
712 // check for <= 0 or NaN with this test 696 // check for <= 0 or NaN with this test
713 if (!(w > 0)) { 697 if (!(w > 0)) {
714 this->lineTo(x2, y2); 698 this->lineTo(x2, y2);
715 } else if (!SkScalarIsFinite(w)) { 699 } else if (!SkScalarIsFinite(w)) {
716 this->lineTo(x1, y1); 700 this->lineTo(x1, y1);
717 this->lineTo(x2, y2); 701 this->lineTo(x2, y2);
718 } else if (SK_Scalar1 == w) { 702 } else if (SK_Scalar1 == w) {
719 this->quadTo(x1, y1, x2, y2); 703 this->quadTo(x1, y1, x2, y2);
720 } else { 704 } else {
721 SkDEBUGCODE(this->validate();) 705 SkDEBUGCODE(this->validate();)
722 706
723 this->injectMoveToIfNeeded(); 707 this->injectMoveToIfNeeded();
724 708
725 SkPathRef::Editor ed(&fPathRef); 709 SkPathRef::Editor ed(&fPathRef);
726 SkPoint* pts = ed.growForConic(w); 710 SkPoint* pts = ed.growForVerb(kConic_Verb, w);
727 pts[0].set(x1, y1); 711 pts[0].set(x1, y1);
728 pts[1].set(x2, y2); 712 pts[1].set(x2, y2);
729 fSegmentMask |= kConic_SegmentMask;
730 713
731 DIRTY_AFTER_EDIT; 714 DIRTY_AFTER_EDIT;
732 } 715 }
733 } 716 }
734 717
735 void SkPath::rConicTo(SkScalar dx1, SkScalar dy1, SkScalar dx2, SkScalar dy2, 718 void SkPath::rConicTo(SkScalar dx1, SkScalar dy1, SkScalar dx2, SkScalar dy2,
736 SkScalar w) { 719 SkScalar w) {
737 this->injectMoveToIfNeeded(); // This can change the result of this->getLas tPt(). 720 this->injectMoveToIfNeeded(); // This can change the result of this->getLas tPt().
738 SkPoint pt; 721 SkPoint pt;
739 this->getLastPt(&pt); 722 this->getLastPt(&pt);
740 this->conicTo(pt.fX + dx1, pt.fY + dy1, pt.fX + dx2, pt.fY + dy2, w); 723 this->conicTo(pt.fX + dx1, pt.fY + dy1, pt.fX + dx2, pt.fY + dy2, w);
741 } 724 }
742 725
743 void SkPath::cubicTo(SkScalar x1, SkScalar y1, SkScalar x2, SkScalar y2, 726 void SkPath::cubicTo(SkScalar x1, SkScalar y1, SkScalar x2, SkScalar y2,
744 SkScalar x3, SkScalar y3) { 727 SkScalar x3, SkScalar y3) {
745 SkDEBUGCODE(this->validate();) 728 SkDEBUGCODE(this->validate();)
746 729
747 this->injectMoveToIfNeeded(); 730 this->injectMoveToIfNeeded();
748 731
749 SkPathRef::Editor ed(&fPathRef); 732 SkPathRef::Editor ed(&fPathRef);
750 SkPoint* pts = ed.growForVerb(kCubic_Verb); 733 SkPoint* pts = ed.growForVerb(kCubic_Verb);
751 pts[0].set(x1, y1); 734 pts[0].set(x1, y1);
752 pts[1].set(x2, y2); 735 pts[1].set(x2, y2);
753 pts[2].set(x3, y3); 736 pts[2].set(x3, y3);
754 fSegmentMask |= kCubic_SegmentMask;
755 737
756 DIRTY_AFTER_EDIT; 738 DIRTY_AFTER_EDIT;
757 } 739 }
758 740
759 void SkPath::rCubicTo(SkScalar x1, SkScalar y1, SkScalar x2, SkScalar y2, 741 void SkPath::rCubicTo(SkScalar x1, SkScalar y1, SkScalar x2, SkScalar y2,
760 SkScalar x3, SkScalar y3) { 742 SkScalar x3, SkScalar y3) {
761 this->injectMoveToIfNeeded(); // This can change the result of this->getLas tPt(). 743 this->injectMoveToIfNeeded(); // This can change the result of this->getLas tPt().
762 SkPoint pt; 744 SkPoint pt;
763 this->getLastPt(&pt); 745 this->getLastPt(&pt);
764 this->cubicTo(pt.fX + x1, pt.fY + y1, pt.fX + x2, pt.fY + y2, 746 this->cubicTo(pt.fX + x1, pt.fY + y1, pt.fX + x2, pt.fY + y2,
(...skipping 66 matching lines...) Expand 10 before | Expand all | Expand 10 after
831 } 813 }
832 this->close(); 814 this->close();
833 } 815 }
834 816
835 void SkPath::addPoly(const SkPoint pts[], int count, bool close) { 817 void SkPath::addPoly(const SkPoint pts[], int count, bool close) {
836 SkDEBUGCODE(this->validate();) 818 SkDEBUGCODE(this->validate();)
837 if (count <= 0) { 819 if (count <= 0) {
838 return; 820 return;
839 } 821 }
840 822
841 SkPathRef::Editor ed(&fPathRef); 823 fLastMoveToIndex = fPathRef->countPoints();
842 fLastMoveToIndex = ed.pathRef()->countPoints(); 824
843 uint8_t* vb;
844 SkPoint* p;
845 // +close makes room for the extra kClose_Verb 825 // +close makes room for the extra kClose_Verb
846 ed.grow(count + close, count, &vb, &p); 826 SkPathRef::Editor ed(&fPathRef, count+close, count);
847 827
848 memcpy(p, pts, count * sizeof(SkPoint)); 828 ed.growForVerb(kMove_Verb)->set(pts[0].fX, pts[0].fY);
849 vb[~0] = kMove_Verb;
850 if (count > 1) { 829 if (count > 1) {
851 // cast to unsigned, so if MIN_COUNT_FOR_MEMSET_TO_BE_FAST is defined to 830 SkPoint* p = ed.growForRepeatedVerb(kLine_Verb, count - 1);
852 // be 0, the compiler will remove the test/branch entirely. 831 memcpy(p, &pts[1], (count-1) * sizeof(SkPoint));
853 if ((unsigned)count >= MIN_COUNT_FOR_MEMSET_TO_BE_FAST) {
854 memset(vb - count, kLine_Verb, count - 1);
855 } else {
856 for (int i = 1; i < count; ++i) {
857 vb[~i] = kLine_Verb;
858 }
859 }
860 fSegmentMask |= kLine_SegmentMask;
861 } 832 }
833
862 if (close) { 834 if (close) {
863 vb[~count] = kClose_Verb; 835 ed.growForVerb(kClose_Verb);
864 } 836 }
865 837
866 DIRTY_AFTER_EDIT; 838 DIRTY_AFTER_EDIT;
867 SkDEBUGCODE(this->validate();) 839 SkDEBUGCODE(this->validate();)
868 } 840 }
869 841
870 #include "SkGeometry.h" 842 #include "SkGeometry.h"
871 843
872 static int build_arc_points(const SkRect& oval, SkScalar startAngle, 844 static int build_arc_points(const SkRect& oval, SkScalar startAngle,
873 SkScalar sweepAngle, 845 SkScalar sweepAngle,
(...skipping 462 matching lines...) Expand 10 before | Expand all | Expand 10 after
1336 const SkScalar kFullCircleAngle = SkIntToScalar(360); 1308 const SkScalar kFullCircleAngle = SkIntToScalar(360);
1337 1309
1338 if (sweepAngle >= kFullCircleAngle || sweepAngle <= -kFullCircleAngle) { 1310 if (sweepAngle >= kFullCircleAngle || sweepAngle <= -kFullCircleAngle) {
1339 this->addOval(oval, sweepAngle > 0 ? kCW_Direction : kCCW_Direction); 1311 this->addOval(oval, sweepAngle > 0 ? kCW_Direction : kCCW_Direction);
1340 return; 1312 return;
1341 } 1313 }
1342 1314
1343 SkPoint pts[kSkBuildQuadArcStorage]; 1315 SkPoint pts[kSkBuildQuadArcStorage];
1344 int count = build_arc_points(oval, startAngle, sweepAngle, pts); 1316 int count = build_arc_points(oval, startAngle, sweepAngle, pts);
1345 1317
1346 this->incReserve(count); 1318 SkDEBUGCODE(this->validate();)
1347 this->moveTo(pts[0]); 1319 SkASSERT(count & 1);
1348 for (int i = 1; i < count; i += 2) { 1320
1349 this->quadTo(pts[i], pts[i+1]); 1321 fLastMoveToIndex = fPathRef->countPoints();
1322
1323 SkPathRef::Editor ed(&fPathRef, 1+(count-1)/2, count);
1324
1325 ed.growForVerb(kMove_Verb)->set(pts[0].fX, pts[0].fY);
1326 if (count > 1) {
1327 SkPoint* p = ed.growForRepeatedVerb(kQuad_Verb, (count-1)/2);
1328 memcpy(p, &pts[1], (count-1) * sizeof(SkPoint));
1350 } 1329 }
1330
1331 DIRTY_AFTER_EDIT;
1332 SkDEBUGCODE(this->validate();)
1351 } 1333 }
1352 1334
1353 /* 1335 /*
1354 Need to handle the case when the angle is sharp, and our computed end-points 1336 Need to handle the case when the angle is sharp, and our computed end-points
1355 for the arc go behind pt1 and/or p2... 1337 for the arc go behind pt1 and/or p2...
1356 */ 1338 */
1357 void SkPath::arcTo(SkScalar x1, SkScalar y1, SkScalar x2, SkScalar y2, 1339 void SkPath::arcTo(SkScalar x1, SkScalar y1, SkScalar x2, SkScalar y2,
1358 SkScalar radius) { 1340 SkScalar radius) {
1359 SkVector before, after; 1341 SkVector before, after;
1360 1342
(...skipping 303 matching lines...) Expand 10 before | Expand all | Expand 10 after
1664 1646
1665 dst->swap(tmp); 1647 dst->swap(tmp);
1666 SkPathRef::Editor ed(&dst->fPathRef); 1648 SkPathRef::Editor ed(&dst->fPathRef);
1667 matrix.mapPoints(ed.points(), ed.pathRef()->countPoints()); 1649 matrix.mapPoints(ed.points(), ed.pathRef()->countPoints());
1668 dst->fDirection = kUnknown_Direction; 1650 dst->fDirection = kUnknown_Direction;
1669 } else { 1651 } else {
1670 SkPathRef::CreateTransformedCopy(&dst->fPathRef, *fPathRef.get(), matrix ); 1652 SkPathRef::CreateTransformedCopy(&dst->fPathRef, *fPathRef.get(), matrix );
1671 1653
1672 if (this != dst) { 1654 if (this != dst) {
1673 dst->fFillType = fFillType; 1655 dst->fFillType = fFillType;
1674 dst->fSegmentMask = fSegmentMask;
1675 dst->fConvexity = fConvexity; 1656 dst->fConvexity = fConvexity;
1676 } 1657 }
1677 1658
1678 if (kUnknown_Direction == fDirection) { 1659 if (kUnknown_Direction == fDirection) {
1679 dst->fDirection = kUnknown_Direction; 1660 dst->fDirection = kUnknown_Direction;
1680 } else { 1661 } else {
1681 SkScalar det2x2 = 1662 SkScalar det2x2 =
1682 SkScalarMul(matrix.get(SkMatrix::kMScaleX), matrix.get(SkMatrix: :kMScaleY)) - 1663 SkScalarMul(matrix.get(SkMatrix::kMScaleX), matrix.get(SkMatrix: :kMScaleY)) -
1683 SkScalarMul(matrix.get(SkMatrix::kMSkewX), matrix.get(SkMatrix:: kMSkewY)); 1664 SkScalarMul(matrix.get(SkMatrix::kMSkewX), matrix.get(SkMatrix:: kMSkewY));
1684 if (det2x2 < 0) { 1665 if (det2x2 < 0) {
(...skipping 353 matching lines...) Expand 10 before | Expand all | Expand 10 after
2038 2019
2039 if (NULL == storage) { 2020 if (NULL == storage) {
2040 const int byteCount = sizeof(int32_t) + fPathRef->writeSize(); 2021 const int byteCount = sizeof(int32_t) + fPathRef->writeSize();
2041 return SkAlign4(byteCount); 2022 return SkAlign4(byteCount);
2042 } 2023 }
2043 2024
2044 SkWBuffer buffer(storage); 2025 SkWBuffer buffer(storage);
2045 2026
2046 int32_t packed = (fConvexity << kConvexity_SerializationShift) | 2027 int32_t packed = (fConvexity << kConvexity_SerializationShift) |
2047 (fFillType << kFillType_SerializationShift) | 2028 (fFillType << kFillType_SerializationShift) |
2048 (fSegmentMask << kSegmentMask_SerializationShift) |
2049 (fDirection << kDirection_SerializationShift) 2029 (fDirection << kDirection_SerializationShift)
2050 #ifndef DELETE_THIS_CODE_WHEN_SKPS_ARE_REBUILT_AT_V16_AND_ALL_OTHER_INSTANCES_TO O 2030 #ifndef DELETE_THIS_CODE_WHEN_SKPS_ARE_REBUILT_AT_V16_AND_ALL_OTHER_INSTANCES_TO O
2051 | (0x1 << kNewFormat_SerializationShift) 2031 | (0x1 << kNewFormat_SerializationShift)
2052 #endif 2032 #endif
2053 ; 2033 ;
2054 2034
2055 buffer.write32(packed); 2035 buffer.write32(packed);
2056 2036
2057 fPathRef->writeToBuffer(&buffer); 2037 fPathRef->writeToBuffer(&buffer);
2058 2038
2059 buffer.padToAlign4(); 2039 buffer.padToAlign4();
2060 return buffer.pos(); 2040 return buffer.pos();
2061 } 2041 }
2062 2042
2063 size_t SkPath::readFromMemory(const void* storage, size_t length) { 2043 size_t SkPath::readFromMemory(const void* storage, size_t length) {
2064 SkRBufferWithSizeCheck buffer(storage, length); 2044 SkRBufferWithSizeCheck buffer(storage, length);
2065 2045
2066 int32_t packed; 2046 int32_t packed;
2067 if (!buffer.readS32(&packed)) { 2047 if (!buffer.readS32(&packed)) {
2068 return 0; 2048 return 0;
2069 } 2049 }
2070 2050
2071 fConvexity = (packed >> kConvexity_SerializationShift) & 0xFF; 2051 fConvexity = (packed >> kConvexity_SerializationShift) & 0xFF;
2072 fFillType = (packed >> kFillType_SerializationShift) & 0xFF; 2052 fFillType = (packed >> kFillType_SerializationShift) & 0xFF;
2073 fSegmentMask = (packed >> kSegmentMask_SerializationShift) & 0xF;
2074 fDirection = (packed >> kDirection_SerializationShift) & 0x3; 2053 fDirection = (packed >> kDirection_SerializationShift) & 0x3;
2075 #ifndef DELETE_THIS_CODE_WHEN_SKPS_ARE_REBUILT_AT_V16_AND_ALL_OTHER_INSTANCES_TO O 2054 #ifndef DELETE_THIS_CODE_WHEN_SKPS_ARE_REBUILT_AT_V16_AND_ALL_OTHER_INSTANCES_TO O
2076 bool newFormat = (packed >> kNewFormat_SerializationShift) & 1; 2055 bool newFormat = (packed >> kNewFormat_SerializationShift) & 1;
2077 #endif 2056 #endif
2078 2057
2079 SkPathRef* pathRef = SkPathRef::CreateFromBuffer(&buffer 2058 SkPathRef* pathRef = SkPathRef::CreateFromBuffer(&buffer
2080 #ifndef DELETE_THIS_CODE_WHEN_SKPS_ARE_REBUILT_AT_V16_AND_ALL_OTHER_INSTANCES_TO O 2059 #ifndef DELETE_THIS_CODE_WHEN_SKPS_ARE_REBUILT_AT_V16_AND_ALL_OTHER_INSTANCES_TO O
2081 , newFormat, packed 2060 , newFormat, packed
2082 #endif 2061 #endif
2083 ); 2062 );
(...skipping 110 matching lines...) Expand 10 before | Expand all | Expand 10 after
2194 } else { 2173 } else {
2195 if (bounds.isEmpty()) { 2174 if (bounds.isEmpty()) {
2196 SkASSERT(fBounds.isEmpty()); 2175 SkASSERT(fBounds.isEmpty());
2197 } else { 2176 } else {
2198 if (!fBounds.isEmpty()) { 2177 if (!fBounds.isEmpty()) {
2199 SkASSERT(fBounds.contains(bounds)); 2178 SkASSERT(fBounds.contains(bounds));
2200 } 2179 }
2201 } 2180 }
2202 } 2181 }
2203 } 2182 }
2204
2205 uint32_t mask = 0;
2206 const uint8_t* verbs = const_cast<const SkPathRef*>(fPathRef.get())->verbs() ;
2207 for (int i = 0; i < fPathRef->countVerbs(); i++) {
2208 switch (verbs[~i]) {
2209 case kLine_Verb:
2210 mask |= kLine_SegmentMask;
2211 break;
2212 case kQuad_Verb:
2213 mask |= kQuad_SegmentMask;
2214 break;
2215 case kConic_Verb:
2216 mask |= kConic_SegmentMask;
2217 break;
2218 case kCubic_Verb:
2219 mask |= kCubic_SegmentMask;
2220 case kMove_Verb: // these verbs aren't included in the segment mask .
2221 case kClose_Verb:
2222 break;
2223 case kDone_Verb:
2224 SkDEBUGFAIL("Done verb shouldn't be recorded.");
2225 break;
2226 default:
2227 SkDEBUGFAIL("Unknown Verb");
2228 break;
2229 }
2230 }
2231 SkASSERT(mask == fSegmentMask);
2232 #endif // SK_DEBUG_PATH 2183 #endif // SK_DEBUG_PATH
2233 } 2184 }
2234 #endif // SK_DEBUG 2185 #endif // SK_DEBUG
2235 2186
2236 /////////////////////////////////////////////////////////////////////////////// 2187 ///////////////////////////////////////////////////////////////////////////////
2237 2188
2238 static int sign(SkScalar x) { return x < 0; } 2189 static int sign(SkScalar x) { return x < 0; }
2239 #define kValueNeverReturnedBySign 2 2190 #define kValueNeverReturnedBySign 2
2240 2191
2241 static bool AlmostEqual(SkScalar compA, SkScalar compB) { 2192 static bool AlmostEqual(SkScalar compA, SkScalar compB) {
(...skipping 660 matching lines...) Expand 10 before | Expand all | Expand 10 after
2902 switch (this->getFillType()) { 2853 switch (this->getFillType()) {
2903 case SkPath::kEvenOdd_FillType: 2854 case SkPath::kEvenOdd_FillType:
2904 case SkPath::kInverseEvenOdd_FillType: 2855 case SkPath::kInverseEvenOdd_FillType:
2905 w &= 1; 2856 w &= 1;
2906 break; 2857 break;
2907 default: 2858 default:
2908 break; 2859 break;
2909 } 2860 }
2910 return SkToBool(w); 2861 return SkToBool(w);
2911 } 2862 }
OLDNEW
« no previous file with comments | « include/core/SkPathRef.h ('k') | src/core/SkPathRef.cpp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698