| Index: src/core/SkPath.cpp
|
| diff --git a/src/core/SkPath.cpp b/src/core/SkPath.cpp
|
| index 738edd9d232c79ea40e9aab40653f5396e971e2f..b92b47f5c6b00f20315618c766b15aff89f0d609 100644
|
| --- a/src/core/SkPath.cpp
|
| +++ b/src/core/SkPath.cpp
|
| @@ -2099,30 +2099,11 @@ static bool almost_equal(SkScalar compA, SkScalar compB) {
|
| return aBits < bBits + epsilon && bBits < aBits + epsilon;
|
| }
|
|
|
| -static DirChange direction_change(const SkPoint& lastPt, const SkVector& curPt,
|
| - const SkVector& lastVec, const SkVector& curVec) {
|
| - SkScalar cross = SkPoint::CrossProduct(lastVec, curVec);
|
| -
|
| - SkScalar smallest = SkTMin(curPt.fX, SkTMin(curPt.fY, SkTMin(lastPt.fX, lastPt.fY)));
|
| - SkScalar largest = SkTMax(curPt.fX, SkTMax(curPt.fY, SkTMax(lastPt.fX, lastPt.fY)));
|
| - largest = SkTMax(largest, -smallest);
|
| -
|
| - if (!almost_equal(largest, largest + cross)) {
|
| - int sign = SkScalarSignAsInt(cross);
|
| - if (sign) {
|
| - return (1 == sign) ? kRight_DirChange : kLeft_DirChange;
|
| - }
|
| - }
|
| -
|
| - if (!SkScalarNearlyZero(lastVec.lengthSqd(), SK_ScalarNearlyZero*SK_ScalarNearlyZero) &&
|
| - !SkScalarNearlyZero(curVec.lengthSqd(), SK_ScalarNearlyZero*SK_ScalarNearlyZero) &&
|
| - lastVec.dot(curVec) < 0.0f) {
|
| - return kBackwards_DirChange;
|
| - }
|
| -
|
| - return kStraight_DirChange;
|
| +static bool approximately_zero_when_compared_to(double x, double y) {
|
| + return x == 0 || fabs(x) < fabs(y * FLT_EPSILON);
|
| }
|
|
|
| +
|
| // only valid for a single contour
|
| struct Convexicator {
|
| Convexicator()
|
| @@ -2161,6 +2142,7 @@ struct Convexicator {
|
| if (!SkScalarIsFinite(lengthSqd)) {
|
| fIsFinite = false;
|
| } else if (!SkScalarNearlyZero(lengthSqd, SK_ScalarNearlyZero*SK_ScalarNearlyZero)) {
|
| + fPriorPt = fLastPt;
|
| fLastPt = fCurrPt;
|
| fCurrPt = pt;
|
| if (++fPtCount == 2) {
|
| @@ -2190,6 +2172,44 @@ struct Convexicator {
|
| }
|
| }
|
|
|
| + DirChange directionChange(const SkVector& curVec) {
|
| + SkScalar cross = SkPoint::CrossProduct(fLastVec, curVec);
|
| +
|
| + SkScalar smallest = SkTMin(fCurrPt.fX, SkTMin(fCurrPt.fY, SkTMin(fLastPt.fX, fLastPt.fY)));
|
| + SkScalar largest = SkTMax(fCurrPt.fX, SkTMax(fCurrPt.fY, SkTMax(fLastPt.fX, fLastPt.fY)));
|
| + largest = SkTMax(largest, -smallest);
|
| +
|
| + if (!almost_equal(largest, largest + cross)) {
|
| + int sign = SkScalarSignAsInt(cross);
|
| + if (sign) {
|
| + return (1 == sign) ? kRight_DirChange : kLeft_DirChange;
|
| + }
|
| + }
|
| +
|
| + if (cross) {
|
| + double dLastVecX = SkScalarToDouble(fLastPt.fX) - SkScalarToDouble(fPriorPt.fX);
|
| + double dLastVecY = SkScalarToDouble(fLastPt.fY) - SkScalarToDouble(fPriorPt.fY);
|
| + double dCurrVecX = SkScalarToDouble(fCurrPt.fX) - SkScalarToDouble(fLastPt.fX);
|
| + double dCurrVecY = SkScalarToDouble(fCurrPt.fY) - SkScalarToDouble(fLastPt.fY);
|
| + double dCross = dLastVecX * dCurrVecY - dLastVecY * dCurrVecX;
|
| + if (!approximately_zero_when_compared_to(dCross, SkScalarToDouble(largest))) {
|
| + int sign = SkScalarSignAsInt(SkDoubleToScalar(dCross));
|
| + if (sign) {
|
| + return (1 == sign) ? kRight_DirChange : kLeft_DirChange;
|
| + }
|
| + }
|
| + }
|
| +
|
| + if (!SkScalarNearlyZero(fLastVec.lengthSqd(), SK_ScalarNearlyZero*SK_ScalarNearlyZero) &&
|
| + !SkScalarNearlyZero(curVec.lengthSqd(), SK_ScalarNearlyZero*SK_ScalarNearlyZero) &&
|
| + fLastVec.dot(curVec) < 0.0f) {
|
| + return kBackwards_DirChange;
|
| + }
|
| +
|
| + return kStraight_DirChange;
|
| + }
|
| +
|
| +
|
| bool isFinite() const {
|
| return fIsFinite;
|
| }
|
| @@ -2201,7 +2221,7 @@ struct Convexicator {
|
| private:
|
| void addVec(const SkVector& vec) {
|
| SkASSERT(vec.fX || vec.fY);
|
| - DirChange dir = direction_change(fLastPt, fCurrPt, fLastVec, vec);
|
| + DirChange dir = this->directionChange(vec);
|
| switch (dir) {
|
| case kLeft_DirChange: // fall through
|
| case kRight_DirChange:
|
| @@ -2230,6 +2250,7 @@ private:
|
| }
|
| }
|
|
|
| + SkPoint fPriorPt;
|
| SkPoint fLastPt;
|
| SkPoint fCurrPt;
|
| // fLastVec does not necessarily start at fLastPt. We only advance it when the cross product
|
|
|