[gtk/wip/otte/lottie: 15/30] stroke: Add miter limit
- From: Benjamin Otte <otte src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gtk/wip/otte/lottie: 15/30] stroke: Add miter limit
- Date: Wed, 2 Dec 2020 02:25:33 +0000 (UTC)
commit 268b1e980b16fa319ebd8be290a0d6c065254f0b
Author: Matthias Clasen <mclasen redhat com>
Date: Sat Nov 28 11:14:59 2020 -0500
stroke: Add miter limit
Add a miter limit to GskStroke. This will be needed to
fully implement line joins.
Also introduce the GSK_LINE_JOIN_MITER_CLIP value,
following SVG 2.0. cairo does not have it, so translate
it to plain miter when using cairo.
docs/reference/gsk/gsk4-sections.txt | 6 +++--
gsk/gskenums.h | 5 +++++
gsk/gskstroke.c | 43 ++++++++++++++++++++++++++++++++++++
gsk/gskstroke.h | 6 +++++
gsk/gskstrokeprivate.h | 1 +
5 files changed, 59 insertions(+), 2 deletions(-)
---
diff --git a/docs/reference/gsk/gsk4-sections.txt b/docs/reference/gsk/gsk4-sections.txt
index 8e50652f9f..53d7545026 100644
--- a/docs/reference/gsk/gsk4-sections.txt
+++ b/docs/reference/gsk/gsk4-sections.txt
@@ -320,10 +320,12 @@ gsk_stroke_free
gsk_stroke_equal
gsk_stroke_set_line_width
gsk_stroke_get_line_width
-gsk_stroke_set_line_cap
-gsk_stroke_get_line_cap
gsk_stroke_set_line_join
gsk_stroke_get_line_join
+gsk_stroke_set_line_cap
+gsk_stroke_get_line_cap
+gsk_stroke_set_miter_limit
+gsk_stroke_get_miter_limit
<SUBSECTION Private>
GSK_TYPE_STROKE
gsk_stroke_get_type
diff --git a/gsk/gskenums.h b/gsk/gskenums.h
index 1ae59dbc3a..aae7587251 100644
--- a/gsk/gskenums.h
+++ b/gsk/gskenums.h
@@ -217,6 +217,7 @@ typedef enum {
/**
* GskLineJoin:
* @GSK_LINE_JOIN_MITER: Use a sharp, angled corner
+ * @GSK_LINE_JOIN_MITER_CLIP: Use a sharp, angled corner, at a distance
* @GSK_LINE_JOIN_ROUND: Use a round join, the center of the circle is
* the joint point
* @GSK_LINE_JOIN_BEVEL: Use a cut-off join, the join is cut off at half
@@ -224,10 +225,14 @@ typedef enum {
*
* Specifies how to render the junction of two lines when stroking.
*
+ * See gsk_stroke_set_miter_limit() for details on the difference between
+ * @GSK_LINE_JOIN_MITER and @GSK_LINE_JOIN_MITER_CLIP.
+ *
* The default line join style is %GSK_LINE_JOIN_MITER.
**/
typedef enum {
GSK_LINE_JOIN_MITER,
+ GSK_LINE_JOIN_MITER_CLIP,
GSK_LINE_JOIN_ROUND,
GSK_LINE_JOIN_BEVEL
} GskLineJoin;
diff --git a/gsk/gskstroke.c b/gsk/gskstroke.c
index 2e6c6293d6..7b72f4ac71 100644
--- a/gsk/gskstroke.c
+++ b/gsk/gskstroke.c
@@ -65,6 +65,9 @@ gsk_stroke_new (float line_width)
self = g_new0 (GskStroke, 1);
self->line_width = line_width;
+ self->line_cap = GSK_LINE_CAP_BUTT;
+ self->line_join = GSK_LINE_JOIN_MITER;
+ self->miter_limit = 4.f; /* following svg */
return self;
}
@@ -135,6 +138,7 @@ gsk_stroke_to_cairo (const GskStroke *self,
switch (self->line_join)
{
case GSK_LINE_JOIN_MITER:
+ case GSK_LINE_JOIN_MITER_CLIP:
cairo_set_line_join (cr, CAIRO_LINE_JOIN_MITER);
break;
case GSK_LINE_JOIN_ROUND:
@@ -147,6 +151,8 @@ gsk_stroke_to_cairo (const GskStroke *self,
g_assert_not_reached ();
break;
}
+
+ cairo_set_miter_limit (cr, self->miter_limit);
}
/**
@@ -268,3 +274,40 @@ gsk_stroke_get_line_join (const GskStroke *self)
return self->line_join;
}
+/**
+ * gsk_stroke_set_miter_limit:
+ * @self: a #GskStroke
+ * @limit: the miter limit, must be non-negative
+ *
+ * Sets the limit for the distance from the corner where sharp
+ * turns of joins get cut off. The miter limit is in units of
+ * line width.
+ *
+ * For joins of type %GSK_LINE_JOIN_MITER that exceed the miter
+ * limit, the join gets rendered as if it was of type
+ * %GSK_LINE_JOIN_BEVEL. For joins of type %GSK_LINE_JOIN_MITER_CLIP,
+ * the miter is clipped at a distance of half the miter limit.
+ */
+void
+gsk_stroke_set_miter_limit (GskStroke *self,
+ float limit)
+{
+ g_return_if_fail (self != NULL);
+ g_return_if_fail (limit >= 0);
+
+ self->miter_limit = limit;
+}
+
+/**
+ * gsk_stroke_get_miter_limit:
+ * @self: a #GskStroke
+ *
+ * Returns the miter limit of a #GskStroke.
+ */
+float
+gsk_stroke_get_miter_limit (const GskStroke *self)
+{
+ g_return_val_if_fail (self != NULL, 4.f);
+
+ return self->miter_limit;
+}
diff --git a/gsk/gskstroke.h b/gsk/gskstroke.h
index df9295adf6..0605262f3e 100644
--- a/gsk/gskstroke.h
+++ b/gsk/gskstroke.h
@@ -60,6 +60,12 @@ void gsk_stroke_set_line_join (GskStroke
GDK_AVAILABLE_IN_ALL
GskLineJoin gsk_stroke_get_line_join (const GskStroke *self);
+GDK_AVAILABLE_IN_ALL
+void gsk_stroke_set_miter_limit (GskStroke *self,
+ float limit);
+GDK_AVAILABLE_IN_ALL
+float gsk_stroke_get_miter_limit (const GskStroke *self);
+
G_END_DECLS
diff --git a/gsk/gskstrokeprivate.h b/gsk/gskstrokeprivate.h
index c6e5c8dc16..850356b1ec 100644
--- a/gsk/gskstrokeprivate.h
+++ b/gsk/gskstrokeprivate.h
@@ -30,6 +30,7 @@ struct _GskStroke
float line_width;
GskLineCap line_cap;
GskLineJoin line_join;
+ float miter_limit;
};
static inline void
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]