diff options
author | commit-bot@chromium.org <commit-bot@chromium.org@2bbb7eff-a529-9590-31e7-b0007b416f81> | 2014-02-21 19:49:10 +0000 |
---|---|---|
committer | commit-bot@chromium.org <commit-bot@chromium.org@2bbb7eff-a529-9590-31e7-b0007b416f81> | 2014-02-21 19:49:10 +0000 |
commit | def6468dd2daed36eced69098445aa99c90487d6 (patch) | |
tree | b3179432d1c09bedaead85474686444bac175caa /src | |
parent | b9882763628bb0f6f14cd05af2d2b435d88e44b2 (diff) |
Stub for conic section max curvature
BUG=skia:
R=reed@google.com
Author: humper@google.com
Review URL: https://codereview.chromium.org/175193003
git-svn-id: http://skia.googlecode.com/svn/trunk@13542 2bbb7eff-a529-9590-31e7-b0007b416f81
Diffstat (limited to 'src')
-rw-r--r-- | src/core/SkGeometry.cpp | 64 |
1 files changed, 44 insertions, 20 deletions
diff --git a/src/core/SkGeometry.cpp b/src/core/SkGeometry.cpp index 76d3a3f4f6..646dfb05b9 100644 --- a/src/core/SkGeometry.cpp +++ b/src/core/SkGeometry.cpp @@ -8,7 +8,9 @@ #include "SkGeometry.h" #include "SkMatrix.h" -bool SkXRayCrossesLine(const SkXRay& pt, const SkPoint pts[2], bool* ambiguous) { +bool SkXRayCrossesLine(const SkXRay& pt, + const SkPoint pts[2], + bool* ambiguous) { if (ambiguous) { *ambiguous = false; } @@ -574,8 +576,8 @@ static void flatten_double_cubic_extrema(SkScalar coords[14]) { } /** Given 4 points on a cubic bezier, chop it into 1, 2, 3 beziers such that - the resulting beziers are monotonic in Y. This is called by the scan converter. - Depending on what is returned, dst[] is treated as follows + the resulting beziers are monotonic in Y. This is called by the scan + converter. Depending on what is returned, dst[] is treated as follows: 0 dst[0..3] is the original cubic 1 dst[0..3] and dst[3..6] are the two new cubics 2 dst[0..3], dst[3..6], dst[6..9] are the three new cubics @@ -632,7 +634,10 @@ int SkFindCubicInflections(const SkPoint src[4], SkScalar tValues[]) { SkScalar Cx = src[3].fX + 3 * (src[1].fX - src[2].fX) - src[0].fX; SkScalar Cy = src[3].fY + 3 * (src[1].fY - src[2].fY) - src[0].fY; - return SkFindUnitQuadRoots(Bx*Cy - By*Cx, Ax*Cy - Ay*Cx, Ax*By - Ay*Bx, tValues); + return SkFindUnitQuadRoots(Bx*Cy - By*Cx, + Ax*Cy - Ay*Cx, + Ax*By - Ay*Bx, + tValues); } int SkChopCubicAtInflections(const SkPoint src[], SkPoint dst[10]) { @@ -963,7 +968,9 @@ bool SkXRayCrossesMonotonicCubic(const SkXRay& pt, const SkPoint cubic[4], return false; } -int SkNumXRayCrossingsForCubic(const SkXRay& pt, const SkPoint cubic[4], bool* ambiguous) { +int SkNumXRayCrossingsForCubic(const SkXRay& pt, + const SkPoint cubic[4], + bool* ambiguous) { int num_crossings = 0; SkPoint monotonic_cubics[10]; int num_monotonic_cubics = SkChopCubicAtYExtrema(cubic, monotonic_cubics); @@ -971,19 +978,25 @@ int SkNumXRayCrossingsForCubic(const SkXRay& pt, const SkPoint cubic[4], bool* a *ambiguous = false; } bool locally_ambiguous; - if (SkXRayCrossesMonotonicCubic(pt, &monotonic_cubics[0], &locally_ambiguous)) + if (SkXRayCrossesMonotonicCubic(pt, + &monotonic_cubics[0], + &locally_ambiguous)) ++num_crossings; if (ambiguous) { *ambiguous |= locally_ambiguous; } if (num_monotonic_cubics > 0) - if (SkXRayCrossesMonotonicCubic(pt, &monotonic_cubics[3], &locally_ambiguous)) + if (SkXRayCrossesMonotonicCubic(pt, + &monotonic_cubics[3], + &locally_ambiguous)) ++num_crossings; if (ambiguous) { *ambiguous |= locally_ambiguous; } if (num_monotonic_cubics > 1) - if (SkXRayCrossesMonotonicCubic(pt, &monotonic_cubics[6], &locally_ambiguous)) + if (SkXRayCrossesMonotonicCubic(pt, + &monotonic_cubics[6], + &locally_ambiguous)) ++num_crossings; if (ambiguous) { *ambiguous |= locally_ambiguous; @@ -1063,9 +1076,10 @@ static bool truncate_last_curve(const SkPoint quad[3], SkScalar x, SkScalar y, static const SkPoint gQuadCirclePts[kSkBuildQuadArcStorage] = { // The mid point of the quadratic arc approximation is half way between the two // control points. The float epsilon adjustment moves the on curve point out by -// two bits, distributing the convex test error between the round rect approximation -// and the convex cross product sign equality test. -#define SK_MID_RRECT_OFFSET (SK_Scalar1 + SK_ScalarTanPIOver8 + FLT_EPSILON * 4) / 2 +// two bits, distributing the convex test error between the round rect +// approximation and the convex cross product sign equality test. +#define SK_MID_RRECT_OFFSET \ + (SK_Scalar1 + SK_ScalarTanPIOver8 + FLT_EPSILON * 4) / 2 { SK_Scalar1, 0 }, { SK_Scalar1, SK_ScalarTanPIOver8 }, { SK_MID_RRECT_OFFSET, SK_MID_RRECT_OFFSET }, @@ -1162,8 +1176,16 @@ int SkBuildQuadArc(const SkVector& uStart, const SkVector& uStop, return pointCount; } -/////////////////////////////////////////////////////////////////////////////// +/////////////////////////////////////////////////////////////////////////////// +// +// NURB representation for conics. Helpful explanations at: +// +// http://citeseerx.ist.psu.edu/viewdoc/ +// download?doi=10.1.1.44.5740&rep=rep1&type=ps +// and +// http://www.cs.mtu.edu/~shene/COURSES/cs3621/NOTES/spline/NURBS/RB-conics.html +// // F = (A (1 - t)^2 + C t^2 + 2 B (1 - t) t w) // ------------------------------------------ // ((1 - t)^2 + t^2 + 2 (1 - t) t w) @@ -1173,12 +1195,6 @@ int SkBuildQuadArc(const SkVector& uStart, const SkVector& uStop, // {t^2 (2 - 2 w), t (-2 + 2 w), 1} // -// Take the parametric specification for the conic (either X or Y) and return -// in coeff[] the coefficients for the simple quadratic polynomial -// coeff[0] for t^2 -// coeff[1] for t -// coeff[2] for constant term -// static SkScalar conic_eval_pos(const SkScalar src[], SkScalar w, SkScalar t) { SkASSERT(src); SkASSERT(t >= 0 && t <= SK_Scalar1); @@ -1210,7 +1226,9 @@ static SkScalar conic_eval_pos(const SkScalar src[], SkScalar w, SkScalar t) { // coeff[1] for t^1 // coeff[2] for t^0 // -static void conic_deriv_coeff(const SkScalar src[], SkScalar w, SkScalar coeff[3]) { +static void conic_deriv_coeff(const SkScalar src[], + SkScalar w, + SkScalar coeff[3]) { const SkScalar P20 = src[4] - src[0]; const SkScalar P10 = src[2] - src[0]; const SkScalar wP10 = w * P10; @@ -1300,7 +1318,8 @@ void SkConic::chopAt(SkScalar t, SkConic dst[2]) const { // or // w1 /= sqrt(w0*w2) // - // However, in our case, we know that for dst[0], w0 == 1, and for dst[1], w2 == 1 + // However, in our case, we know that for dst[0]: + // w0 == 1, and for dst[1], w2 == 1 // SkScalar root = SkScalarSqrt(tmp2[1].fZ); dst[0].fW = tmp2[0].fZ / root; @@ -1442,3 +1461,8 @@ void SkConic::computeTightBounds(SkRect* bounds) const { void SkConic::computeFastBounds(SkRect* bounds) const { bounds->set(fPts, 3); } + +bool SkConic::findMaxCurvature(SkScalar* t) const { + // TODO: Implement me + return false; +} |