Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
/*
|
|
|
|
* Copyright 2012 Google Inc.
|
|
|
|
*
|
|
|
|
* Use of this source code is governed by a BSD-style license that can be
|
|
|
|
* found in the LICENSE file.
|
|
|
|
*/
|
2013-07-08 17:17:02 +00:00
|
|
|
#include "SkGeometry.h"
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
#include "SkOpEdgeBuilder.h"
|
|
|
|
#include "SkReduceOrder.h"
|
|
|
|
|
|
|
|
void SkOpEdgeBuilder::init() {
|
2015-03-26 14:52:43 +00:00
|
|
|
fCurrentContour = fContoursHead;
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
fOperand = false;
|
|
|
|
fXorMask[0] = fXorMask[1] = (fPath->getFillType() & 1) ? kEvenOdd_PathOpsMask
|
|
|
|
: kWinding_PathOpsMask;
|
2013-04-26 19:51:16 +00:00
|
|
|
fUnparseable = false;
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
fSecondHalf = preFetch();
|
|
|
|
}
|
|
|
|
|
|
|
|
void SkOpEdgeBuilder::addOperand(const SkPath& path) {
|
|
|
|
SkASSERT(fPathVerbs.count() > 0 && fPathVerbs.end()[-1] == SkPath::kDone_Verb);
|
2015-03-26 14:52:43 +00:00
|
|
|
fPathVerbs.pop();
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
fPath = &path;
|
|
|
|
fXorMask[1] = (fPath->getFillType() & 1) ? kEvenOdd_PathOpsMask
|
|
|
|
: kWinding_PathOpsMask;
|
|
|
|
preFetch();
|
|
|
|
}
|
|
|
|
|
2015-03-26 14:52:43 +00:00
|
|
|
int SkOpEdgeBuilder::count() const {
|
|
|
|
SkOpContour* contour = fContoursHead;
|
|
|
|
int count = 0;
|
|
|
|
while (contour) {
|
|
|
|
count += contour->count() > 0;
|
|
|
|
contour = contour->next();
|
|
|
|
}
|
|
|
|
return count;
|
|
|
|
}
|
|
|
|
|
2016-07-18 17:01:36 +00:00
|
|
|
bool SkOpEdgeBuilder::finish() {
|
2015-03-26 14:52:43 +00:00
|
|
|
fOperand = false;
|
2016-07-18 17:01:36 +00:00
|
|
|
if (fUnparseable || !walk()) {
|
2013-04-26 19:51:16 +00:00
|
|
|
return false;
|
|
|
|
}
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
complete();
|
2015-03-26 14:52:43 +00:00
|
|
|
if (fCurrentContour && !fCurrentContour->count()) {
|
|
|
|
fContoursHead->remove(fCurrentContour);
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
}
|
2013-07-08 17:17:02 +00:00
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
|
|
|
void SkOpEdgeBuilder::closeContour(const SkPoint& curveEnd, const SkPoint& curveStart) {
|
2013-11-01 17:36:03 +00:00
|
|
|
if (!SkDPoint::ApproximatelyEqual(curveEnd, curveStart)) {
|
2015-03-26 14:52:43 +00:00
|
|
|
*fPathVerbs.append() = SkPath::kLine_Verb;
|
|
|
|
*fPathPts.append() = curveStart;
|
2013-07-08 17:17:02 +00:00
|
|
|
} else {
|
2013-11-01 17:36:03 +00:00
|
|
|
fPathPts[fPathPts.count() - 1] = curveStart;
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
}
|
2015-03-26 14:52:43 +00:00
|
|
|
*fPathVerbs.append() = SkPath::kClose_Verb;
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
}
|
|
|
|
|
2014-09-18 17:32:57 +00:00
|
|
|
// very tiny points cause numerical instability : don't allow them
|
|
|
|
static void force_small_to_zero(SkPoint* pt) {
|
|
|
|
if (SkScalarAbs(pt->fX) < FLT_EPSILON_ORDERABLE_ERR) {
|
|
|
|
pt->fX = 0;
|
|
|
|
}
|
|
|
|
if (SkScalarAbs(pt->fY) < FLT_EPSILON_ORDERABLE_ERR) {
|
|
|
|
pt->fY = 0;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
int SkOpEdgeBuilder::preFetch() {
|
2013-04-26 19:51:16 +00:00
|
|
|
if (!fPath->isFinite()) {
|
|
|
|
fUnparseable = true;
|
|
|
|
return 0;
|
|
|
|
}
|
2013-04-25 11:51:54 +00:00
|
|
|
SkPath::RawIter iter(*fPath);
|
2013-07-08 17:17:02 +00:00
|
|
|
SkPoint curveStart;
|
|
|
|
SkPoint curve[4];
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
SkPoint pts[4];
|
|
|
|
SkPath::Verb verb;
|
2013-07-08 17:17:02 +00:00
|
|
|
bool lastCurve = false;
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
do {
|
|
|
|
verb = iter.next(pts);
|
2013-07-08 17:17:02 +00:00
|
|
|
switch (verb) {
|
|
|
|
case SkPath::kMove_Verb:
|
|
|
|
if (!fAllowOpenContours && lastCurve) {
|
|
|
|
closeContour(curve[0], curveStart);
|
|
|
|
}
|
2015-03-26 14:52:43 +00:00
|
|
|
*fPathVerbs.append() = verb;
|
2014-09-18 17:32:57 +00:00
|
|
|
force_small_to_zero(&pts[0]);
|
2015-03-26 14:52:43 +00:00
|
|
|
*fPathPts.append() = pts[0];
|
2013-07-08 17:17:02 +00:00
|
|
|
curveStart = curve[0] = pts[0];
|
|
|
|
lastCurve = false;
|
|
|
|
continue;
|
|
|
|
case SkPath::kLine_Verb:
|
2014-09-18 17:32:57 +00:00
|
|
|
force_small_to_zero(&pts[1]);
|
2013-11-01 17:36:03 +00:00
|
|
|
if (SkDPoint::ApproximatelyEqual(curve[0], pts[1])) {
|
2015-03-26 14:52:43 +00:00
|
|
|
uint8_t lastVerb = fPathVerbs.top();
|
2013-11-01 17:36:03 +00:00
|
|
|
if (lastVerb != SkPath::kLine_Verb && lastVerb != SkPath::kMove_Verb) {
|
2015-03-26 14:52:43 +00:00
|
|
|
fPathPts.top() = pts[1];
|
2013-09-16 15:55:01 +00:00
|
|
|
}
|
2013-07-08 17:17:02 +00:00
|
|
|
continue; // skip degenerate points
|
|
|
|
}
|
|
|
|
break;
|
|
|
|
case SkPath::kQuad_Verb:
|
2014-09-18 17:32:57 +00:00
|
|
|
force_small_to_zero(&pts[1]);
|
|
|
|
force_small_to_zero(&pts[2]);
|
2013-07-08 17:17:02 +00:00
|
|
|
curve[1] = pts[1];
|
|
|
|
curve[2] = pts[2];
|
|
|
|
verb = SkReduceOrder::Quad(curve, pts);
|
|
|
|
if (verb == SkPath::kMove_Verb) {
|
|
|
|
continue; // skip degenerate points
|
|
|
|
}
|
|
|
|
break;
|
2015-04-20 15:31:59 +00:00
|
|
|
case SkPath::kConic_Verb:
|
|
|
|
force_small_to_zero(&pts[1]);
|
|
|
|
force_small_to_zero(&pts[2]);
|
|
|
|
curve[1] = pts[1];
|
|
|
|
curve[2] = pts[2];
|
|
|
|
verb = SkReduceOrder::Conic(curve, iter.conicWeight(), pts);
|
|
|
|
if (verb == SkPath::kMove_Verb) {
|
|
|
|
continue; // skip degenerate points
|
2013-07-08 17:17:02 +00:00
|
|
|
}
|
2015-04-20 15:31:59 +00:00
|
|
|
break;
|
2013-07-08 17:17:02 +00:00
|
|
|
case SkPath::kCubic_Verb:
|
2014-09-18 17:32:57 +00:00
|
|
|
force_small_to_zero(&pts[1]);
|
|
|
|
force_small_to_zero(&pts[2]);
|
|
|
|
force_small_to_zero(&pts[3]);
|
2013-07-08 17:17:02 +00:00
|
|
|
curve[1] = pts[1];
|
|
|
|
curve[2] = pts[2];
|
|
|
|
curve[3] = pts[3];
|
|
|
|
verb = SkReduceOrder::Cubic(curve, pts);
|
|
|
|
if (verb == SkPath::kMove_Verb) {
|
|
|
|
continue; // skip degenerate points
|
|
|
|
}
|
|
|
|
break;
|
|
|
|
case SkPath::kClose_Verb:
|
|
|
|
closeContour(curve[0], curveStart);
|
|
|
|
lastCurve = false;
|
|
|
|
continue;
|
|
|
|
case SkPath::kDone_Verb:
|
|
|
|
continue;
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
}
|
2015-03-26 14:52:43 +00:00
|
|
|
*fPathVerbs.append() = verb;
|
2013-07-08 17:17:02 +00:00
|
|
|
int ptCount = SkPathOpsVerbToPoints(verb);
|
2015-03-26 14:52:43 +00:00
|
|
|
fPathPts.append(ptCount, &pts[1]);
|
2015-04-20 15:31:59 +00:00
|
|
|
if (verb == SkPath::kConic_Verb) {
|
|
|
|
*fWeights.append() = iter.conicWeight();
|
|
|
|
}
|
2013-07-08 17:17:02 +00:00
|
|
|
curve[0] = pts[ptCount];
|
|
|
|
lastCurve = true;
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
} while (verb != SkPath::kDone_Verb);
|
2013-07-08 17:17:02 +00:00
|
|
|
if (!fAllowOpenContours && lastCurve) {
|
|
|
|
closeContour(curve[0], curveStart);
|
|
|
|
}
|
2015-03-26 14:52:43 +00:00
|
|
|
*fPathVerbs.append() = SkPath::kDone_Verb;
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
return fPathVerbs.count() - 1;
|
|
|
|
}
|
|
|
|
|
2013-04-26 19:51:16 +00:00
|
|
|
bool SkOpEdgeBuilder::close() {
|
|
|
|
complete();
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
2016-07-18 17:01:36 +00:00
|
|
|
bool SkOpEdgeBuilder::walk() {
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
uint8_t* verbPtr = fPathVerbs.begin();
|
|
|
|
uint8_t* endOfFirstHalf = &verbPtr[fSecondHalf];
|
2015-03-26 14:52:43 +00:00
|
|
|
SkPoint* pointsPtr = fPathPts.begin() - 1;
|
2015-04-20 15:31:59 +00:00
|
|
|
SkScalar* weightPtr = fWeights.begin();
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
SkPath::Verb verb;
|
2013-04-25 11:51:54 +00:00
|
|
|
while ((verb = (SkPath::Verb) *verbPtr) != SkPath::kDone_Verb) {
|
|
|
|
if (verbPtr == endOfFirstHalf) {
|
|
|
|
fOperand = true;
|
|
|
|
}
|
|
|
|
verbPtr++;
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
switch (verb) {
|
|
|
|
case SkPath::kMove_Verb:
|
2015-03-26 14:52:43 +00:00
|
|
|
if (fCurrentContour && fCurrentContour->count()) {
|
2013-04-26 19:51:16 +00:00
|
|
|
if (fAllowOpenContours) {
|
|
|
|
complete();
|
|
|
|
} else if (!close()) {
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
}
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
if (!fCurrentContour) {
|
2016-07-18 17:01:36 +00:00
|
|
|
fCurrentContour = fContoursHead->appendContour();
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
}
|
2015-03-26 14:52:43 +00:00
|
|
|
fCurrentContour->init(fGlobalState, fOperand,
|
|
|
|
fXorMask[fOperand] == kEvenOdd_PathOpsMask);
|
2013-07-08 17:17:02 +00:00
|
|
|
pointsPtr += 1;
|
2013-04-25 11:51:54 +00:00
|
|
|
continue;
|
2013-07-08 17:17:02 +00:00
|
|
|
case SkPath::kLine_Verb:
|
2016-07-18 17:01:36 +00:00
|
|
|
fCurrentContour->addLine(pointsPtr);
|
2013-07-08 17:17:02 +00:00
|
|
|
break;
|
|
|
|
case SkPath::kQuad_Verb:
|
2016-07-18 17:01:36 +00:00
|
|
|
fCurrentContour->addQuad(pointsPtr);
|
2013-07-08 17:17:02 +00:00
|
|
|
break;
|
2015-04-20 15:31:59 +00:00
|
|
|
case SkPath::kConic_Verb:
|
2016-07-18 17:01:36 +00:00
|
|
|
fCurrentContour->addConic(pointsPtr, *weightPtr++);
|
2015-04-20 15:31:59 +00:00
|
|
|
break;
|
2015-03-26 14:52:43 +00:00
|
|
|
case SkPath::kCubic_Verb: {
|
2016-04-26 21:12:22 +00:00
|
|
|
// Split complex cubics (such as self-intersecting curves or
|
|
|
|
// ones with difficult curvature) in two before proceeding.
|
|
|
|
// This can be required for intersection to succeed.
|
|
|
|
SkScalar splitT;
|
|
|
|
if (SkDCubic::ComplexBreak(pointsPtr, &splitT)) {
|
|
|
|
SkPoint cubicPair[7];
|
|
|
|
SkChopCubicAt(pointsPtr, cubicPair, splitT);
|
2015-04-20 15:31:59 +00:00
|
|
|
if (!SkScalarsAreFinite(&cubicPair[0].fX, SK_ARRAY_COUNT(cubicPair) * 2)) {
|
|
|
|
return false;
|
|
|
|
}
|
2015-03-26 14:52:43 +00:00
|
|
|
SkPoint cStorage[2][4];
|
|
|
|
SkPath::Verb v1 = SkReduceOrder::Cubic(&cubicPair[0], cStorage[0]);
|
|
|
|
SkPath::Verb v2 = SkReduceOrder::Cubic(&cubicPair[3], cStorage[1]);
|
|
|
|
if (v1 != SkPath::kMove_Verb && v2 != SkPath::kMove_Verb) {
|
|
|
|
SkPoint* curve1 = v1 == SkPath::kCubic_Verb ? &cubicPair[0] : cStorage[0];
|
|
|
|
SkPoint* curve2 = v2 == SkPath::kCubic_Verb ? &cubicPair[3] : cStorage[1];
|
|
|
|
for (int index = 0; index < SkPathOpsVerbToPoints(v1); ++index) {
|
|
|
|
force_small_to_zero(&curve1[index]);
|
|
|
|
}
|
|
|
|
for (int index = 0; index < SkPathOpsVerbToPoints(v2); ++index) {
|
|
|
|
force_small_to_zero(&curve2[index]);
|
|
|
|
}
|
2016-08-23 14:38:48 +00:00
|
|
|
if (SkPath::kLine_Verb != v1 ||
|
|
|
|
!SkDPoint::ApproximatelyEqual(curve1[0], curve1[1])) {
|
|
|
|
fCurrentContour->addCurve(v1, curve1);
|
|
|
|
}
|
|
|
|
if (SkPath::kLine_Verb != v2 ||
|
|
|
|
!SkDPoint::ApproximatelyEqual(curve2[0], curve2[1])) {
|
|
|
|
fCurrentContour->addCurve(v2, curve2);
|
|
|
|
}
|
2015-03-26 14:52:43 +00:00
|
|
|
} else {
|
2016-07-18 17:01:36 +00:00
|
|
|
fCurrentContour->addCubic(pointsPtr);
|
2015-03-26 14:52:43 +00:00
|
|
|
}
|
|
|
|
} else {
|
2016-07-18 17:01:36 +00:00
|
|
|
fCurrentContour->addCubic(pointsPtr);
|
2015-03-26 14:52:43 +00:00
|
|
|
}
|
|
|
|
} break;
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
case SkPath::kClose_Verb:
|
|
|
|
SkASSERT(fCurrentContour);
|
2013-04-26 19:51:16 +00:00
|
|
|
if (!close()) {
|
|
|
|
return false;
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
}
|
2013-04-25 11:51:54 +00:00
|
|
|
continue;
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
default:
|
|
|
|
SkDEBUGFAIL("bad verb");
|
2013-04-26 19:51:16 +00:00
|
|
|
return false;
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
}
|
2015-03-24 20:55:33 +00:00
|
|
|
SkASSERT(fCurrentContour);
|
2015-03-26 14:52:43 +00:00
|
|
|
fCurrentContour->debugValidate();
|
|
|
|
pointsPtr += SkPathOpsVerbToPoints(verb);
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
}
|
2015-03-26 14:52:43 +00:00
|
|
|
if (fCurrentContour && fCurrentContour->count() &&!fAllowOpenContours && !close()) {
|
2013-04-26 19:51:16 +00:00
|
|
|
return false;
|
|
|
|
}
|
|
|
|
return true;
|
Add base types for path ops
Paths contain lines, quads, and cubics, which are
collectively curves.
To work with path intersections, intermediary curves
are constructed. For now, those intermediates use
doubles to guarantee sufficient precision.
The DVector, DPoint, DLine, DQuad, and DCubic
structs encapsulate these intermediate curves.
The DRect and DTriangle structs are created to
describe intersectable areas of interest.
The Bounds struct inherits from SkRect to create
a SkScalar-based rectangle that intersects shared
edges.
This also includes common math equalities and
debugging that the remainder of path ops builds on,
as well as a temporary top-level interface in
include/pathops/SkPathOps.h.
Review URL: https://codereview.chromium.org/12827020
git-svn-id: http://skia.googlecode.com/svn/trunk@8551 2bbb7eff-a529-9590-31e7-b0007b416f81
2013-04-08 11:47:37 +00:00
|
|
|
}
|