[gtk/wip/otte/lottie: 11/83] gsk: Add GskStroke




commit 5244b51457308d77e230b1646ca07f19d54bb50e
Author: Benjamin Otte <otte redhat com>
Date:   Wed Nov 25 16:21:50 2020 +0100

    gsk: Add GskStroke
    
    It's unused in this commit. This just prepares the new object.

 docs/reference/gsk/gsk4-docs.xml     |   1 +
 docs/reference/gsk/gsk4-sections.txt |  19 +++
 gsk/gsk.h                            |   1 +
 gsk/gskenums.h                       |  38 ++++-
 gsk/gskstroke.c                      | 270 +++++++++++++++++++++++++++++++++++
 gsk/gskstroke.h                      |  66 +++++++++
 gsk/gskstrokeprivate.h               |  53 +++++++
 gsk/gsktypes.h                       |   1 +
 gsk/meson.build                      |   2 +
 9 files changed, 450 insertions(+), 1 deletion(-)
---
diff --git a/docs/reference/gsk/gsk4-docs.xml b/docs/reference/gsk/gsk4-docs.xml
index 268631bf90..b79f7a24ec 100644
--- a/docs/reference/gsk/gsk4-docs.xml
+++ b/docs/reference/gsk/gsk4-docs.xml
@@ -27,6 +27,7 @@
     <title>Paths</title>
     <xi:include href="xml/GskPath.xml" />
     <xi:include href="xml/GskPathBuilder.xml" />
+    <xi:include href="xml/GskStroke.xml" />
   </part>
 
   <index id="api-index-full">
diff --git a/docs/reference/gsk/gsk4-sections.txt b/docs/reference/gsk/gsk4-sections.txt
index 8ffe2a490a..b1fa4cae56 100644
--- a/docs/reference/gsk/gsk4-sections.txt
+++ b/docs/reference/gsk/gsk4-sections.txt
@@ -354,6 +354,25 @@ GSK_TYPE_PATH_BUILDER
 gsk_path_builder_get_type
 </SECTION>
 
+<SECTION>
+<FILE>GskStroke</FILE>
+GskLineCap
+GskLineJoin
+gsk_stroke_new
+gsk_stroke_copy
+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
+<SUBSECTION Private>
+GSK_TYPE_STROKE
+gsk_stroke_get_type
+</SECTION>
+
 <SECTION>
 <FILE>GskTransform</FILE>
 GskTransform
diff --git a/gsk/gsk.h b/gsk/gsk.h
index 2adfa3aec0..a5b530f291 100644
--- a/gsk/gsk.h
+++ b/gsk/gsk.h
@@ -26,6 +26,7 @@
 #include <gsk/gskrenderer.h>
 #include <gsk/gskrendernode.h>
 #include <gsk/gskroundedrect.h>
+#include <gsk/gskstroke.h>
 #include <gsk/gsktransform.h>
 
 #include <gsk/gskcairorenderer.h>
diff --git a/gsk/gskenums.h b/gsk/gskenums.h
index 5048559866..141bb46797 100644
--- a/gsk/gskenums.h
+++ b/gsk/gskenums.h
@@ -196,6 +196,43 @@ typedef enum {
   GSK_FILL_RULE_EVEN_ODD
 } GskFillRule;
 
+/**
+ * @GSK_LINE_CAP_BUTT: Start and stop the line exactly at the start
+ *     and end point
+ * @GSK_LINE_CAP_ROUND: Use a round ending, the center of the circle
+ *     is the start or end point.
+ * @GSK_LINE_CAP_SQUARE: use squared ending, the center of the square
+ *     is the start or end point.
+ *
+ * Specifies how to render the start and end points of contours or
+ * dashes when stroking.
+ *
+ * The default line cap style is %GSK_LINE_CAP_BUTT.
+ */
+typedef enum {
+  GSK_LINE_CAP_BUTT,
+  GSK_LINE_CAP_ROUND,
+  GSK_LINE_CAP_SQUARE
+} GskLineCap;
+
+/**
+ * GskLineJoin:
+ * @GSK_LINE_JOIN_MITER: Use a shart angled corner
+ * @GSK_LINE_JOIN_ROUND: Use a round join, the center of the circle is
+ *     the joing point
+ * @GSK_LINE_JOIN_BEVEL: use a cut-off join, the join is cut off at half
+ *     the line width from the joint point
+ *
+ * Specifies how to render the junction of two lines when stroking.
+ *
+ * The default line join style is %GSK_LINE_JOIN_MITER.
+ **/
+typedef enum {
+  GSK_LINE_JOIN_MITER,
+  GSK_LINE_JOIN_ROUND,
+  GSK_LINE_JOIN_BEVEL
+} GskLineJoin;
+
 /**
  * GskSerializationError:
  * @GSK_SERIALIZATION_UNSUPPORTED_FORMAT: The format can not be
@@ -278,5 +315,4 @@ typedef enum
   GSK_GL_UNIFORM_TYPE_VEC4,
 } GskGLUniformType;
 
-
 #endif /* __GSK_TYPES_H__ */
diff --git a/gsk/gskstroke.c b/gsk/gskstroke.c
new file mode 100644
index 0000000000..2e6c6293d6
--- /dev/null
+++ b/gsk/gskstroke.c
@@ -0,0 +1,270 @@
+/*
+ * Copyright © 2020 Benjamin Otte
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library. If not, see <http://www.gnu.org/licenses/>.
+ *
+ * Authors: Benjamin Otte <otte gnome org>
+ */
+
+#include "config.h"
+
+#include "gskstrokeprivate.h"
+
+/**
+ * SECTION:gskstroke
+ * @Title: Stroke
+ * @Short_description: Properties of a stroke operation
+ * @See_also: #GskPath, gsk_stroke_node_new()
+ *
+ * This section describes the #GskStroke structure that is used to
+ * describe lines and curves that are more complex than simple rectangles.
+ *
+ * #GskStroke is an immutable struct. After creation, you cannot change
+ * the types it represents. Instead, new #GskStroke have to be created.
+ * The #GskStrokeBuilder structure is meant to help in this endeavor.
+ */
+
+/**
+ * GskStroke:
+ *
+ * A #GskStroke struct is an opaque struct that should be copied
+ * on use.
+ */
+
+G_DEFINE_BOXED_TYPE (GskStroke, gsk_stroke,
+                     gsk_stroke_copy,
+                     gsk_stroke_free)
+
+
+/**
+ * gsk_stroke_new:
+ * @line_width: line width of the stroke. Must be > 0
+ *
+ * Creates a new #GskStroke with the given @line_width.
+ *
+ * Returns: a new #GskStroke
+ **/
+GskStroke *
+gsk_stroke_new (float line_width)
+{
+  GskStroke *self;
+
+  g_return_val_if_fail (line_width > 0, NULL);
+
+  self = g_new0 (GskStroke, 1);
+
+  self->line_width = line_width;
+
+  return self;
+}
+
+/**
+ * gsk_stroke_copy:
+ * @other: #GskStroke to copy
+ *
+ * Creates a copy of the given @other stroke.
+ *
+ * Returns: a new #GskStroke. Use gsk_stroke_free() to free it.
+ **/
+GskStroke *
+gsk_stroke_copy (const GskStroke *other)
+{
+  GskStroke *self;
+
+  g_return_val_if_fail (other != NULL, NULL);
+
+  self = g_new (GskStroke, 1);
+
+  gsk_stroke_init_copy (self, other);
+
+  return self;
+}
+
+/**
+ * gsk_stroke_free:
+ * @self: a #GskStroke
+ *
+ * Frees a #GskStroke.
+ **/
+void
+gsk_stroke_free (GskStroke *self)
+{
+  if (self == NULL)
+    return;
+
+  gsk_stroke_clear (self);
+
+  g_free (self);
+}
+
+void
+gsk_stroke_to_cairo (const GskStroke *self,
+                     cairo_t         *cr)
+{
+  cairo_set_line_width (cr, self->line_width);
+
+  /* gcc can optimize that to a direct case. This catches later additions to the enum */
+  switch (self->line_cap)
+    {
+      case GSK_LINE_CAP_BUTT:
+        cairo_set_line_cap (cr, CAIRO_LINE_CAP_BUTT);
+        break;
+      case GSK_LINE_CAP_ROUND:
+        cairo_set_line_cap (cr, CAIRO_LINE_CAP_ROUND);
+        break;
+      case GSK_LINE_CAP_SQUARE:
+        cairo_set_line_cap (cr, CAIRO_LINE_CAP_SQUARE);
+        break;
+      default:
+        g_assert_not_reached ();
+        break;
+    }
+
+  /* gcc can optimize that to a direct case. This catches later additions to the enum */
+  switch (self->line_join)
+    {
+      case GSK_LINE_JOIN_MITER:
+        cairo_set_line_join (cr, CAIRO_LINE_JOIN_MITER);
+        break;
+      case GSK_LINE_JOIN_ROUND:
+        cairo_set_line_join (cr, CAIRO_LINE_JOIN_ROUND);
+        break;
+      case GSK_LINE_JOIN_BEVEL:
+        cairo_set_line_join (cr, CAIRO_LINE_JOIN_BEVEL);
+        break;
+      default:
+        g_assert_not_reached ();
+        break;
+    }
+}
+
+/**
+ * gsk_stroke_equal:
+ * @stroke1: the first #GskStroke
+ * @stroke2: the second #GskStroke
+ *
+ * Checks if 2 strokes are identical.
+ *
+ * Returns: %TRUE if the 2 strokes are equal, %FALSE otherwise
+ **/
+gboolean
+gsk_stroke_equal (gconstpointer stroke1,
+                  gconstpointer stroke2)
+{
+  const GskStroke *self1 = stroke1;
+  const GskStroke *self2 = stroke2;
+
+  return self1->line_width == self2->line_width;
+}
+
+/**
+ * gsk_stroke_set_line_width:
+ * @self: a #GskStroke
+ * @line_width: width of the line in pixels
+ *
+ * Sets the line width to be used when stroking. The line width
+ * must be > 0.
+ **/
+void
+gsk_stroke_set_line_width (GskStroke *self,
+                           float      line_width)
+{
+  g_return_if_fail (self != NULL);
+  g_return_if_fail (line_width > 0);
+
+  self->line_width = line_width;
+}
+
+/**
+ * gsk_stroke_get_line_width:
+ * @self: a #GskStroke
+ *
+ * Gets the line width used.
+ *
+ * Returns: The line width
+ **/
+float
+gsk_stroke_get_line_width (const GskStroke *self)
+{
+  g_return_val_if_fail (self != NULL, 0.0);
+
+  return self->line_width;
+}
+
+/**
+ * gsk_stroke_set_line_cap:
+ * @self: a #GskStroke
+ * @line_cap: the #GskLineCap
+ *
+ * Sets the line cap to be used when stroking.
+ * See #GskLineCap for details.
+ **/
+void
+gsk_stroke_set_line_cap (GskStroke  *self,
+                         GskLineCap  line_cap)
+{
+  g_return_if_fail (self != NULL);
+
+  self->line_cap = line_cap;
+}
+
+/**
+ * gsk_stroke_get_line_cap:
+ * @self: a #GskStroke
+ *
+ * Gets the line cap used. See #GskLineCap for details.
+ *
+ * Returns: The line cap
+ **/
+GskLineCap
+gsk_stroke_get_line_cap (const GskStroke *self)
+{
+  g_return_val_if_fail (self != NULL, 0.0);
+
+  return self->line_cap;
+}
+
+/**
+ * gsk_stroke_set_line_join:
+ * @self: a #GskStroke
+ * @line_join: The line join to use
+ *
+ * Sets the line join to be used when stroking.
+ * See #GskLineJoin for details.
+ **/
+void
+gsk_stroke_set_line_join (GskStroke   *self,
+                          GskLineJoin  line_join)
+{
+  g_return_if_fail (self != NULL);
+
+  self->line_join = line_join;
+}
+
+/**
+ * gsk_stroke_get_line_join:
+ * @self: a #GskStroke
+ *
+ * Gets the line join used. See #GskLineJoin for details.
+ *
+ * Returns: The line join
+ **/
+GskLineJoin
+gsk_stroke_get_line_join (const GskStroke *self)
+{
+  g_return_val_if_fail (self != NULL, 0.0);
+
+  return self->line_join;
+}
+
diff --git a/gsk/gskstroke.h b/gsk/gskstroke.h
new file mode 100644
index 0000000000..df9295adf6
--- /dev/null
+++ b/gsk/gskstroke.h
@@ -0,0 +1,66 @@
+/*
+ * Copyright © 2020 Benjamin Otte
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library. If not, see <http://www.gnu.org/licenses/>.
+ *
+ * Authors: Benjamin Otte <otte gnome org>
+ */
+
+#ifndef __GSK_STROKE_H__
+#define __GSK_STROKE_H__
+
+#if !defined (__GSK_H_INSIDE__) && !defined (GTK_COMPILATION)
+#error "Only <gsk/gsk.h> can be included directly."
+#endif
+
+
+#include <gsk/gsktypes.h>
+
+G_BEGIN_DECLS
+
+#define GSK_TYPE_STROKE (gsk_stroke_get_type ())
+
+GDK_AVAILABLE_IN_ALL
+GType                   gsk_stroke_get_type                     (void) G_GNUC_CONST;
+GDK_AVAILABLE_IN_ALL
+GskStroke *             gsk_stroke_new                          (float                   line_width);
+GDK_AVAILABLE_IN_ALL
+GskStroke *             gsk_stroke_copy                         (const GskStroke        *other);
+GDK_AVAILABLE_IN_ALL
+void                    gsk_stroke_free                         (GskStroke              *self);
+
+GDK_AVAILABLE_IN_ALL
+gboolean                gsk_stroke_equal                        (gconstpointer           stroke1,
+                                                                 gconstpointer           stroke2);
+
+GDK_AVAILABLE_IN_ALL
+void                    gsk_stroke_set_line_width               (GskStroke              *self,
+                                                                 float                   line_width);
+GDK_AVAILABLE_IN_ALL
+float                   gsk_stroke_get_line_width               (const GskStroke        *self);
+GDK_AVAILABLE_IN_ALL
+void                    gsk_stroke_set_line_cap                 (GskStroke              *self,
+                                                                 GskLineCap              line_cap);
+GDK_AVAILABLE_IN_ALL
+GskLineCap              gsk_stroke_get_line_cap                 (const GskStroke        *self);
+GDK_AVAILABLE_IN_ALL
+void                    gsk_stroke_set_line_join                (GskStroke              *self,
+                                                                 GskLineJoin             line_join);
+GDK_AVAILABLE_IN_ALL
+GskLineJoin             gsk_stroke_get_line_join                (const GskStroke        *self);
+
+
+G_END_DECLS
+
+#endif /* __GSK_STROKE_H__ */
diff --git a/gsk/gskstrokeprivate.h b/gsk/gskstrokeprivate.h
new file mode 100644
index 0000000000..c6e5c8dc16
--- /dev/null
+++ b/gsk/gskstrokeprivate.h
@@ -0,0 +1,53 @@
+/*
+ * Copyright © 2020 Benjamin Otte
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library. If not, see <http://www.gnu.org/licenses/>.
+ *
+ * Authors: Benjamin Otte <otte gnome org>
+ */
+
+
+#ifndef __GSK_STROKE_PRIVATE_H__
+#define __GSK_STROKE_PRIVATE_H__
+
+#include "gskstroke.h"
+
+G_BEGIN_DECLS
+
+struct _GskStroke
+{
+  float line_width;
+  GskLineCap line_cap;
+  GskLineJoin line_join;
+};
+
+static inline void
+gsk_stroke_init_copy (GskStroke       *stroke,
+                      const GskStroke *other)
+{
+  *stroke = *other;
+}
+
+static inline void
+gsk_stroke_clear (GskStroke *stroke)
+{
+}
+
+void                    gsk_stroke_to_cairo                     (const GskStroke        *self,
+                                                                 cairo_t                *cr);
+
+G_END_DECLS
+
+#endif /* __GSK_STROKE_PRIVATE_H__ */
+
diff --git a/gsk/gsktypes.h b/gsk/gsktypes.h
index 863ef651c2..fdf06b5ffc 100644
--- a/gsk/gsktypes.h
+++ b/gsk/gsktypes.h
@@ -28,6 +28,7 @@
 
 typedef struct _GskPath                 GskPath;
 typedef struct _GskRenderer             GskRenderer;
+typedef struct _GskStroke               GskStroke;
 typedef struct _GskTransform            GskTransform;
 
 #endif /* __GSK_TYPES_H__ */
diff --git a/gsk/meson.build b/gsk/meson.build
index 3747b9278e..c11b857fcf 100644
--- a/gsk/meson.build
+++ b/gsk/meson.build
@@ -30,6 +30,7 @@ gsk_public_sources = files([
   'gskrendernodeimpl.c',
   'gskrendernodeparser.c',
   'gskroundedrect.c',
+  'gskstroke.c',
   'gsktransform.c',
   'gl/gskglrenderer.c',
 ])
@@ -59,6 +60,7 @@ gsk_public_headers = files([
   'gskrenderer.h',
   'gskrendernode.h',
   'gskroundedrect.h',
+  'gskstroke.h',
   'gsktransform.h',
   'gsktypes.h',
   'gsk-autocleanup.h',


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]