[gtk/path-work-rebased: 24/123] spline: Use Skia's tolerance checks
- From: Matthias Clasen <matthiasc src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gtk/path-work-rebased: 24/123] spline: Use Skia's tolerance checks
- Date: Thu, 7 Apr 2022 20:40:55 +0000 (UTC)
commit dbe87eed63c99aa6dca2e24c3284bade81c2d144
Author: Benjamin Otte <otte redhat com>
Date: Wed Nov 25 02:18:34 2020 +0100
spline: Use Skia's tolerance checks
This avoids measuring being too far off (it's still off, but it's less
than a percent now.
gsk/gskpathprivate.h | 4 ++--
gsk/gskspline.c | 26 +++++++++++++++++++++++---
2 files changed, 25 insertions(+), 5 deletions(-)
---
diff --git a/gsk/gskpathprivate.h b/gsk/gskpathprivate.h
index 7af9dbcaff..34ec4a549a 100644
--- a/gsk/gskpathprivate.h
+++ b/gsk/gskpathprivate.h
@@ -25,8 +25,8 @@
G_BEGIN_DECLS
-/* Same as Cairo, so looks like a good value. ¯\_(ツ)_/¯ */
-#define GSK_PATH_TOLERANCE_DEFAULT (0.1)
+/* Same as Skia, so looks like a good value. ¯\_(ツ)_/¯ */
+#define GSK_PATH_TOLERANCE_DEFAULT (0.5)
gsize gsk_path_get_n_contours (GskPath *path);
gboolean gsk_path_foreach_with_tolerance (GskPath *self,
diff --git a/gsk/gskspline.c b/gsk/gskspline.c
index e1e7f39c53..d429e9d04f 100644
--- a/gsk/gskspline.c
+++ b/gsk/gskspline.c
@@ -29,7 +29,7 @@ typedef struct
{
graphene_point_t last_point;
float last_progress;
- float tolerance_squared;
+ float tolerance;
GskSplineAddPointFunc func;
gpointer user_data;
} GskCubicDecomposition;
@@ -103,6 +103,7 @@ gsk_spline_split_cubic (const graphene_point_t pts[4],
memcpy (result2, (graphene_point_t[4]) { final, bccd, cd, pts[3] }, sizeof (graphene_point_t[4]));
}
+#if 0
/* Return an upper bound on the error (squared) that could result from
* approximating a spline as a line segment connecting the two endpoints. */
static float
@@ -180,6 +181,25 @@ gsk_spline_error_squared (const graphene_point_t pts[4])
else
return cerr;
}
+#endif
+
+/* taken from Skia, including the very descriptive name */
+static gboolean
+gsk_spline_cubic_too_curvy (const graphene_point_t pts[4],
+ float tolerance)
+{
+ graphene_point_t p;
+
+ graphene_point_interpolate (&pts[0], &pts[3], 1.0f / 3, &p);
+ if (ABS (p.x - pts[1].x) + ABS (p.y - pts[1].y) > tolerance)
+ return TRUE;
+
+ graphene_point_interpolate (&pts[0], &pts[3], 2.0f / 3, &p);
+ if (ABS (p.x - pts[2].x) + ABS (p.y - pts[2].y) > tolerance)
+ return TRUE;
+
+ return FALSE;
+}
static void
gsk_spline_decompose_into (GskCubicDecomposition *decomp,
@@ -188,7 +208,7 @@ gsk_spline_decompose_into (GskCubicDecomposition *decomp,
{
graphene_point_t left[4], right[4];
- if (gsk_spline_error_squared (pts) < decomp->tolerance_squared)
+ if (!gsk_spline_cubic_too_curvy (pts, decomp->tolerance) || progress < 1 / 1024.f)
{
gsk_spline_decompose_add_point (decomp, &pts[3], progress);
return;
@@ -206,7 +226,7 @@ gsk_spline_decompose_cubic (const graphene_point_t pts[4],
GskSplineAddPointFunc add_point_func,
gpointer user_data)
{
- GskCubicDecomposition decomp = { pts[0], 0.0f, tolerance * tolerance, add_point_func, user_data };
+ GskCubicDecomposition decomp = { pts[0], 0.0f, tolerance, add_point_func, user_data };
gsk_spline_decompose_into (&decomp, pts, 1.0f);
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]