Add arc methods to path builder

Bug: skia:9000
Change-Id: I0a25c6f792f59230762651386da74e547b073930
Reviewed-on: https://skia-review.googlesource.com/c/skia/+/307558
Reviewed-by: Mike Reed <reed@google.com>
Commit-Queue: Mike Reed <reed@google.com>
diff --git a/gm/aarectmodes.cpp b/gm/aarectmodes.cpp
index cd14096..31e6ef6 100644
--- a/gm/aarectmodes.cpp
+++ b/gm/aarectmodes.cpp
@@ -14,6 +14,7 @@
 #include "include/core/SkMatrix.h"
 #include "include/core/SkPaint.h"
 #include "include/core/SkPath.h"
+#include "include/core/SkPathBuilder.h"
 #include "include/core/SkPoint.h"
 #include "include/core/SkRect.h"
 #include "include/core/SkRefCnt.h"
@@ -44,7 +45,7 @@
         0, 1, 1, 1, 4,
         0, 1, 1, 1, 4
     };
-    SkPath path;
+    SkPathBuilder path;
     SkPoint* ptPtr = pts;
     for (size_t i = 0; i < sizeof(verbs); ++i) {
         switch ((SkPath::Verb) verbs[i]) {
@@ -66,7 +67,7 @@
     }
     SkRect clip = {0, 130, 772, 531};
     canvas->clipRect(clip);
-    canvas->drawPath(path, paint);
+    canvas->drawPath(path.detach(), paint);
 }
 
 constexpr SkBlendMode gModes[] = {
diff --git a/gm/addarc.cpp b/gm/addarc.cpp
index eeed7d6..3f4d578 100644
--- a/gm/addarc.cpp
+++ b/gm/addarc.cpp
@@ -10,6 +10,7 @@
 #include "include/core/SkColor.h"
 #include "include/core/SkPaint.h"
 #include "include/core/SkPath.h"
+#include "include/core/SkPathBuilder.h"
 #include "include/core/SkPathMeasure.h"
 #include "include/core/SkPoint.h"
 #include "include/core/SkRect.h"
@@ -215,7 +216,7 @@
 
 //////////////////////
 
-static void html_canvas_arc(SkPath* path, SkScalar x, SkScalar y, SkScalar r, SkScalar start,
+static void html_canvas_arc(SkPathBuilder* path, SkScalar x, SkScalar y, SkScalar r, SkScalar start,
                             SkScalar end, bool ccw, bool callArcTo) {
     SkRect bounds = { x - r, y - r, x + r, y + r };
     SkScalar sweep = ccw ? end - start : start - end;
@@ -257,12 +258,12 @@
             SkScalar startAngle = startAngles[i % SK_ARRAY_COUNT(startAngles)] * sign;
             canvas->save();
             for (size_t j = 0; j < SK_ARRAY_COUNT(sweepAngles); ++j) {
-                SkPath path;
+                SkPathBuilder path;
                 path.moveTo(0, 2);
                 html_canvas_arc(&path, 18, 15, 10, startAngle, startAngle + (sweepAngles[j] * sign),
                                 anticlockwise, true);
                 path.lineTo(0, 28);
-                canvas->drawPath(path, paint);
+                canvas->drawPath(path.detach(), paint);
                 canvas->translate(30, 0);
             }
             canvas->restore();
@@ -286,7 +287,7 @@
         SkScalar sweepAngle = 10.0f / outerRadius;
 
         for (size_t i = 0; i < SK_ARRAY_COUNT(startAngles); ++i) {
-            SkPath path;
+            SkPathBuilder path;
             SkScalar endAngle = startAngles[i] + sweepAngle;
             path.moveTo(centerX + innerRadius * sk_float_cos(startAngles[i]),
                         centerY + innerRadius * sk_float_sin(startAngles[i]));
@@ -301,7 +302,7 @@
             html_canvas_arc(&path, centerX, outerRadius, innerRadius,
                             endAngle * 180 / SK_ScalarPI, startAngles[i] * 180 / SK_ScalarPI,
                             true, false);
-            canvas->drawPath(path, paint);
+            canvas->drawPath(path.detach(), paint);
             canvas->translate(20, 0);
         }
 }
diff --git a/gm/arcto.cpp b/gm/arcto.cpp
index 03942fe..20528c8 100644
--- a/gm/arcto.cpp
+++ b/gm/arcto.cpp
@@ -9,7 +9,7 @@
 #include "include/core/SkCanvas.h"
 #include "include/core/SkColor.h"
 #include "include/core/SkPaint.h"
-#include "include/core/SkPath.h"
+#include "include/core/SkPathBuilder.h"
 #include "include/core/SkPathEffect.h"
 #include "include/core/SkPathMeasure.h"
 #include "include/core/SkRect.h"
@@ -72,23 +72,21 @@
     paint.setColor(0xFF660000);
 //    canvas->scale(2, 2);  // for testing on retina
     SkRect oval = SkRect::MakeXYWH(100, 100, 100, 100);
-    SkPath svgArc;
 
-    for (int angle = 0; angle <= 45; angle += 45) {
-       for (int oHeight = 2; oHeight >= 1; --oHeight) {
+    for (SkScalar angle = 0; angle <= 45; angle += 45) {
+        for (int oHeight = 2; oHeight >= 1; --oHeight) {
+            SkPathBuilder svgArc;
             SkScalar ovalHeight = oval.height() / oHeight;
             svgArc.moveTo(oval.fLeft, oval.fTop);
-            svgArc.arcTo(oval.width() / 2, ovalHeight, SkIntToScalar(angle), SkPath::kSmall_ArcSize,
-                    SkPathDirection::kCW, oval.right(), oval.bottom());
-            canvas->drawPath(svgArc, paint);
-            svgArc.reset();
+            svgArc.arcTo({oval.width() / 2, ovalHeight}, angle, SkPathBuilder::kSmall_ArcSize,
+                         SkPathDirection::kCW, {oval.right(), oval.bottom()});
+            canvas->drawPath(svgArc.detach(), paint);
 
             svgArc.moveTo(oval.fLeft + 100, oval.fTop + 100);
-            svgArc.arcTo(oval.width() / 2, ovalHeight, SkIntToScalar(angle), SkPath::kLarge_ArcSize,
-                    SkPathDirection::kCCW, oval.right(), oval.bottom() + 100);
-            canvas->drawPath(svgArc, paint);
+            svgArc.arcTo({oval.width() / 2, ovalHeight}, angle, SkPathBuilder::kLarge_ArcSize,
+                         SkPathDirection::kCCW, {oval.right(), oval.bottom() + 100});
+            canvas->drawPath(svgArc.detach(), paint);
             oval.offset(50, 0);
-            svgArc.reset();
 
         }
     }
@@ -105,22 +103,22 @@
     };
     int cIndex = 0;
     for (const char* arcstr : arcstrs) {
-        SkParsePath::FromSVGString(arcstr, &svgArc);
+        SkPath path;
+        SkParsePath::FromSVGString(arcstr, &path);
         paint.setColor(colors[cIndex++]);
-        canvas->drawPath(svgArc, paint);
+        canvas->drawPath(path, paint);
     }
 
     // test that zero length arcs still draw round cap
     paint.setStrokeCap(SkPaint::kRound_Cap);
-    SkPath path;
-    path.moveTo(100, 100);
-    path.arcTo(0, 0, 0, SkPath::kLarge_ArcSize, SkPathDirection::kCW, 200, 200);
-    canvas->drawPath(path, paint);
+    SkPathBuilder path;
+    path.moveTo(100, 100)
+        .arcTo({0, 0}, 0, SkPathBuilder::kLarge_ArcSize, SkPathDirection::kCW, {200, 200});
+    canvas->drawPath(path.detach(), paint);
 
-    path.reset();
-    path.moveTo(200, 100);
-    path.arcTo(80, 80, 0, SkPath::kLarge_ArcSize, SkPathDirection::kCW, 200, 100);
-    canvas->drawPath(path, paint);
+    path.moveTo(200, 100)
+        .arcTo({80, 80}, 0, SkPathBuilder::kLarge_ArcSize, SkPathDirection::kCW, {200, 100});
+    canvas->drawPath(path.detach(), paint);
 }
 
 enum {
@@ -200,7 +198,7 @@
 DEF_SIMPLE_GM(bug593049, canvas, 300, 300) {
     canvas->translate(111, 0);
 
-    SkPath p;
+    SkPathBuilder p;
     p.moveTo(-43.44464063610148f, 79.43535936389853f);
     const SkScalar yOffset = 122.88f;
     const SkScalar radius = 61.44f;
@@ -212,7 +210,7 @@
     paint.setStrokeCap(SkPaint::kRound_Cap);
     paint.setStrokeWidth(15.36f);
 
-    canvas->drawPath(p, paint);
+    canvas->drawPath(p.detach(), paint);
 }
 
 DEF_SIMPLE_GM(bug583299, canvas, 300, 300) {
diff --git a/gm/complexclip3.cpp b/gm/complexclip3.cpp
index b6fea1f..3c160e0 100644
--- a/gm/complexclip3.cpp
+++ b/gm/complexclip3.cpp
@@ -11,7 +11,7 @@
 #include "include/core/SkColor.h"
 #include "include/core/SkFont.h"
 #include "include/core/SkPaint.h"
-#include "include/core/SkPath.h"
+#include "include/core/SkPathBuilder.h"
 #include "include/core/SkRect.h"
 #include "include/core/SkScalar.h"
 #include "include/core/SkSize.h"
@@ -45,21 +45,18 @@
     SkISize onISize() override { return SkISize::Make(400, 950); }
 
     void onDraw(SkCanvas* canvas) override {
-        SkPath clipSimple;
-        clipSimple.addCircle(SkIntToScalar(70), SkIntToScalar(50), SkIntToScalar(20));
+        SkPath clipSimple = SkPath::Circle(70, 50, 20);
 
         SkRect r1 = { 10, 20, 70, 80 };
-        SkPath clipComplex;
-        clipComplex.moveTo(SkIntToScalar(40),  SkIntToScalar(50));
-        clipComplex.arcTo(r1, SkIntToScalar(30), SkIntToScalar(300), false);
-        clipComplex.close();
+        SkPath clipComplex = SkPathBuilder().moveTo(40,  50)
+                                            .arcTo(r1, 30, 300, false)
+                                            .close()
+                                            .detach();
 
         SkPath* firstClip = &clipSimple;
         SkPath* secondClip = &clipComplex;
-
         if (!fDoSimpleClipFirst) {
-            using std::swap;
-            swap(firstClip, secondClip);
+            std::swap(firstClip, secondClip);
         }
 
         SkPaint paint;
diff --git a/gm/conicpaths.cpp b/gm/conicpaths.cpp
index f3ceaea..f68edbd 100644
--- a/gm/conicpaths.cpp
+++ b/gm/conicpaths.cpp
@@ -156,9 +156,9 @@
     paint.setAntiAlias(true);
     paint.setStroke(true);
     canvas->drawCircle(c, radius, paint);
-    SkPath path;
-    path.moveTo(288.88884710654133f, -280.26680862609f);
-    path.arcTo(0, 0, -39.00216443306411f, 400.6058925796476f, radius);
+    SkPath path = SkPathBuilder().moveTo(288.88884710654133f, -280.26680862609f)
+                                 .arcTo({0, 0}, {-39.00216443306411f, 400.6058925796476f}, radius)
+                                 .detach();
     paint.setColor(0xff007f00);
     canvas->drawPath(path, paint);
 }
diff --git a/gm/crbug_996140.cpp b/gm/crbug_996140.cpp
index d2d2b6d..1cc6097 100644
--- a/gm/crbug_996140.cpp
+++ b/gm/crbug_996140.cpp
@@ -9,7 +9,7 @@
 #include "include/core/SkCanvas.h"
 #include "include/core/SkColor.h"
 #include "include/core/SkPaint.h"
-#include "include/core/SkPath.h"
+#include "include/core/SkPathBuilder.h"
 
 /*
  * Canvas example. Expected large blue stroked circle, white middle, small red circle.
@@ -43,7 +43,6 @@
     canvas->translate(-800, -200);
 
     // 3: ctx.beginPath();
-    SkPath path;
 
     // 4: ctx.scale(203.20, 203.20);
     canvas->scale(s, s);
@@ -66,8 +65,10 @@
     // 9: ctx.arc(19.221, 720-6.76,0.0295275590551181,0,2*Math.PI);
     // This matches how Canvas prepares an arc(x, y, radius, 0, 2pi) call
     SkRect boundingBox = SkRect::MakeLTRB(cx - radius, cy - radius, cx + radius, cy + radius);
-    path.arcTo(boundingBox, 0, 180.f, false);
-    path.arcTo(boundingBox, 180.f, 180.f, false);
+
+    auto path = SkPathBuilder().arcTo(boundingBox, 0, 180.f, false)
+                               .arcTo(boundingBox, 180.f, 180.f, false)
+                               .detach();
 
     // 12: ctx.closePath();
     // path.close();
diff --git a/gm/overstroke.cpp b/gm/overstroke.cpp
index 6352a94..ecac1bb 100644
--- a/gm/overstroke.cpp
+++ b/gm/overstroke.cpp
@@ -26,7 +26,7 @@
 #include "include/core/SkCanvas.h"
 #include "include/core/SkColor.h"
 #include "include/core/SkPaint.h"
-#include "include/core/SkPath.h"
+#include "include/core/SkPathBuilder.h"
 #include "include/core/SkPathMeasure.h"
 #include "include/core/SkPoint.h"
 #include "include/core/SkRect.h"
@@ -83,11 +83,7 @@
 SkPath oval_path() {
     SkRect oval = SkRect::MakeXYWH(0, -25, 100, 50);
 
-    SkPath path;
-    path.arcTo(oval, 0, 359, true);
-    path.close();
-
-    return path;
+    return SkPathBuilder().arcTo(oval, 0, 359, true).close().detach();
 }
 
 SkPath ribs_path(SkPath path, SkScalar radius) {
diff --git a/gm/patharcto.cpp b/gm/patharcto.cpp
index 1350033..d67033d 100644
--- a/gm/patharcto.cpp
+++ b/gm/patharcto.cpp
@@ -8,7 +8,7 @@
 #include "gm/gm.h"
 #include "include/core/SkCanvas.h"
 #include "include/core/SkPaint.h"
-#include "include/core/SkPath.h"
+#include "include/core/SkPathBuilder.h"
 
 // crbug.com/982968
 // Intended to draw a curvy triangle.
@@ -18,25 +18,25 @@
 // The fix was to use doubles for this part of the calc in SkPath::arcTo().
 //
 DEF_SIMPLE_GM(shallow_angle_path_arcto, canvas, 300, 300) {
-    SkPath path;
+    SkPathBuilder path;
     SkPaint paint;
     paint.setStyle(SkPaint::kStroke_Style);
 
-    path.moveTo(313.44189096331155f, 106.6009423589212f);
-    path.arcTo(284.3113082008462f, 207.1407719157063f,
-               255.15053777129728f, 307.6718505416374f,
-               697212.0011054524f);
-    path.lineTo(255.15053777129728f, 307.6718505416374f);
-    path.arcTo(340.4737465981018f, 252.6907319346971f,
-               433.54333477716153f, 212.18116363345337f,
-               1251.2484277907251f);
-    path.lineTo(433.54333477716153f, 212.18116363345337f);
-    path.arcTo(350.19513833839466f, 185.89280014838369f,
-               313.44189096331155f, 106.6009423589212f,
+    path.moveTo(313.44189096331155f, 106.6009423589212f)
+        .arcTo({284.3113082008462f, 207.1407719157063f},
+               {255.15053777129728f, 307.6718505416374f},
+               697212.0011054524f)
+        .lineTo(255.15053777129728f, 307.6718505416374f)
+        .arcTo({340.4737465981018f, 252.6907319346971f},
+               {433.54333477716153f, 212.18116363345337f},
+               1251.2484277907251f)
+        .lineTo(433.54333477716153f, 212.18116363345337f)
+        .arcTo({350.19513833839466f, 185.89280014838369f},
+               {313.44189096331155f, 106.6009423589212f},
                198.03116885327813f);
 
     canvas->translate(-200, -50);
-    canvas->drawPath(path, paint);
+    canvas->drawPath(path.detach(), paint);
 };
 
 #include "include/utils/SkParsePath.h"
diff --git a/gm/pathfill.cpp b/gm/pathfill.cpp
index 9d908cb..17244c5 100644
--- a/gm/pathfill.cpp
+++ b/gm/pathfill.cpp
@@ -9,7 +9,7 @@
 #include "include/core/SkCanvas.h"
 #include "include/core/SkColor.h"
 #include "include/core/SkPaint.h"
-#include "include/core/SkPath.h"
+#include "include/core/SkPathBuilder.h"
 #include "include/core/SkRect.h"
 #include "include/core/SkScalar.h"
 #include "include/core/SkSize.h"
@@ -668,7 +668,7 @@
     p.setStyle(SkPaint::kStroke_Style);
     p.setStrokeWidth(2);
 
-    SkPath path;
+    SkPathBuilder path;
     SkPoint pts[] = { {20, 20}, {100, 20}, {100, 60}, {130, 150}, {180, 160} };
     SkScalar radius = 60;
     path.moveTo(pts[0]);
@@ -676,5 +676,5 @@
     path.lineTo(pts[2]);
     path.close();
     path.arcTo(pts[3], pts[4], radius);
-    canvas->drawPath(path, p);
+    canvas->drawPath(path.detach(), p);
 }