[goffice] Fixed more doc issues and add some GOPath new API.
- From: Jean BrÃfort <jbrefort src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [goffice] Fixed more doc issues and add some GOPath new API.
- Date: Mon, 20 Aug 2012 12:27:15 +0000 (UTC)
commit 14a989acc7ec45316e125652291630b1bfe2357b
Author: Jean Brefort <jean brefort normalesup org>
Date: Mon Aug 20 14:24:40 2012 +0200
Fixed more doc issues and add some GOPath new API.
ChangeLog | 10 +
docs/reference/goffice-docs.xml | 1 +
goffice/graph/gog-styled-object.c | 8 +
goffice/utils/go-cairo.c | 180 +-------------
goffice/utils/go-path.c | 506 ++++++++++++++++++++++++++++++++++++-
goffice/utils/go-path.h | 10 +-
6 files changed, 538 insertions(+), 177 deletions(-)
---
diff --git a/ChangeLog b/ChangeLog
index ff1a35a..ae2a93f 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,13 @@
+2012-08-20 Jean Brefort <jean brefort normalesup org>
+
+ * docs/reference/goffice-docs.xml: fixed a few more doc issues.
+ * goffice/graph/gog-styled-object.c (gog_styled_object_class_init): ditto.
+ * goffice/utils/go-cairo.c (go_cairo_emit_svg_path): use
+ go_path_new_from_svg().
+ * goffice/utils/go-path.c (go_path_scale),
+ (go_path_new_from_svg), (go_path_new_from_odf_enhanced_path): new functions.
+ * goffice/utils/go-path.h: ditto.
+
2012-08-16 Jean Brefort <jean brefort normalesup org>
* configure.in: requires libgsf-1 >= 1.14.23 for introspection.
diff --git a/docs/reference/goffice-docs.xml b/docs/reference/goffice-docs.xml
index 2e0794b..8567871 100644
--- a/docs/reference/goffice-docs.xml
+++ b/docs/reference/goffice-docs.xml
@@ -161,6 +161,7 @@
<chapter>
<title>File utilities</title>
<xi:include href="xml/go-file.xml"/>
+ <xi:include href="xml/file.xml"/>
<xi:include href="xml/go-file-opener.xml"/>
<xi:include href="xml/go-file-saver.xml"/>
<xi:include href="xml/go-url.xml"/>
diff --git a/goffice/graph/gog-styled-object.c b/goffice/graph/gog-styled-object.c
index 231f6b6..cab83bd 100644
--- a/goffice/graph/gog-styled-object.c
+++ b/goffice/graph/gog-styled-object.c
@@ -188,6 +188,14 @@ gog_styled_object_class_init (GogObjectClass *gog_klass)
GObjectClass *gobject_klass = (GObjectClass *) gog_klass;
GogStyledObjectClass *style_klass = (GogStyledObjectClass *) gog_klass;
+ /**
+ * GogStyledObject::style-changed:
+ * @object: the object on which the signal is emitted
+ * @style: The new #GOStyle
+ *
+ * The ::style-changed signal is emitted after the style has been changed
+ * by a call to go_styled_object_set_style().
+ **/
gog_styled_object_signals [STYLE_CHANGED] = g_signal_new ("style-changed",
G_TYPE_FROM_CLASS (gog_klass),
G_SIGNAL_RUN_LAST,
diff --git a/goffice/utils/go-cairo.c b/goffice/utils/go-cairo.c
index 0871b7d..39ec88a 100644
--- a/goffice/utils/go-cairo.c
+++ b/goffice/utils/go-cairo.c
@@ -20,154 +20,9 @@
*/
#include <goffice/utils/go-cairo.h>
+#include <goffice/goffice.h>
#include <math.h>
-static void
-skip_spaces (char **path)
-{
- while (**path == ' ')
- (*path)++;
-}
-
-static void
-skip_comma_and_spaces (char **path)
-{
- while (**path == ' ' || **path == ',')
- (*path)++;
-}
-
-static gboolean
-parse_value (char **path, double *x)
-{
- char *end, *c;
- gboolean integer_part = FALSE;
- gboolean fractional_part = FALSE;
- gboolean exponent_part = FALSE;
- double mantissa = 0.0;
- double exponent =0.0;
- double divisor;
- gboolean mantissa_sign = 1.0;
- gboolean exponent_sign = 1.0;
-
- c = *path;
-
- if (*c == '-') {
- mantissa_sign = -1.0;
- c++;
- } else if (*c == '+')
- c++;
-
- if (*c >= '0' && *c <= '9') {
- integer_part = TRUE;
- mantissa = *c - '0';
- c++;
-
- while (*c >= '0' && *c <= '9') {
- mantissa = mantissa * 10.0 + *c - '0';
- c++;
- }
- }
-
-
- if (*c == '.')
- c++;
- else if (!integer_part)
- return FALSE;
-
- if (*c >= '0' && *c <= '9') {
- fractional_part = TRUE;
- mantissa += (*c - '0') * 0.1;
- divisor = 0.01;
- c++;
-
- while (*c >= '0' && *c <= '9') {
- mantissa += (*c - '0') * divisor;
- divisor *= 0.1;
- c++;
- }
- }
-
- if (!fractional_part && !integer_part)
- return FALSE;
-
- end = c;
-
- if (*c == 'E' || *c == 'e') {
- c++;
-
- if (*c == '-') {
- exponent_sign = -1.0;
- c++;
- } else if (*c == '+')
- c++;
-
- if (*c >= '0' && *c <= '9') {
- exponent_part = TRUE;
- exponent = *c - '0';
- c++;
-
- while (*c >= '0' && *c <= '9') {
- exponent = exponent * 10.0 + *c - '0';
- c++;
- }
- }
-
- }
-
- if (exponent_part) {
- end = c;
- *x = mantissa_sign * mantissa * pow (10.0, exponent_sign * exponent);
- } else
- *x = mantissa_sign * mantissa;
-
- *path = end;
-
- return TRUE;
-}
-
-static gboolean
-parse_values (char **path, unsigned int n_values, double *values)
-{
- char *ptr = *path;
- unsigned int i;
-
- skip_comma_and_spaces (path);
-
- for (i = 0; i < n_values; i++) {
- if (!parse_value (path, &values[i])) {
- *path = ptr;
- return FALSE;
- }
- skip_comma_and_spaces (path);
- }
-
- return TRUE;
-}
-
-static void
-emit_function_2 (char **path, cairo_t *cr,
- void (*cairo_func) (cairo_t *, double, double))
-{
- double values[2];
-
- skip_spaces (path);
-
- while (parse_values (path, 2, values))
- cairo_func (cr, values[0], values[1]);
-}
-
-static void
-emit_function_6 (char **path, cairo_t *cr,
- void (*cairo_func) (cairo_t *, double, double, double ,double, double, double))
-{
- double values[6];
-
- skip_spaces (path);
-
- while (parse_values (path, 6, values))
- cairo_func (cr, values[0], values[1], values[2], values[3], values[4], values[5]);
-}
-
/**
* go_cairo_emit_svg_path:
* @cr: a cairo context
@@ -181,39 +36,14 @@ void
go_cairo_emit_svg_path (cairo_t *cr, char const *path)
{
char *ptr;
+ GOPath *go_path;
if (path == NULL)
return;
- ptr = (char *) path;
-
- skip_spaces (&ptr);
-
- while (*ptr != '\0') {
- if (*ptr == 'M') {
- ptr++;
- emit_function_2 (&ptr, cr, cairo_move_to);
- } else if (*ptr == 'm') {
- ptr++;
- emit_function_2 (&ptr, cr, cairo_rel_move_to);
- } else if (*ptr == 'L') {
- ptr++;
- emit_function_2 (&ptr, cr, cairo_line_to);
- } else if (*ptr == 'l') {
- ptr++;
- emit_function_2 (&ptr, cr, cairo_rel_line_to);
- } else if (*ptr == 'C') {
- ptr++;
- emit_function_6 (&ptr, cr, cairo_curve_to);
- } else if (*ptr == 'c') {
- ptr++;
- emit_function_6 (&ptr, cr, cairo_rel_curve_to);
- } else if (*ptr == 'Z' || *ptr == 'z') {
- ptr++;
- cairo_close_path (cr);
- } else
- ptr++;
- }
+ go_path = go_path_new_from_svg (path);
+ go_path_to_cairo (go_path, GO_PATH_DIRECTION_FORWARD, cr);
+ go_path_free (go_path);
}
gboolean
diff --git a/goffice/utils/go-path.c b/goffice/utils/go-path.c
index 5ccebad..9c3f5c2 100644
--- a/goffice/utils/go-path.c
+++ b/goffice/utils/go-path.c
@@ -109,6 +109,14 @@
* GOPathDirection:
* @GO_PATH_DIRECTION_FORWARD: go through the pass from start to end.
* @GO_PATH_DIRECTION_BACKWARD: go through the pass from end to start.
+ * @GO_PATH_DIRECTION_FORWARD_SKIP_NO_FILL: go through the pass from start to end,
+ * skipping segments markes as no-fill.
+ * @GO_PATH_DIRECTION_BACKWARD_SKIP_NO_FILL: go through the pass from end to start,
+ * skipping segments markes as no-fill.
+ * @GO_PATH_DIRECTION_FORWARD_SKIP_NO_STROKE: go through the pass from start to end,
+ * skipping segments markes as no-stroke.
+ * @GO_PATH_DIRECTION_BACKWARD_SKIP_NO_STROKE: go through the pass from end to start,
+ * skipping segments markes as no-stroke.
**/
#define GO_PATH_DEFAULT_BUFFER_SIZE 64
@@ -120,7 +128,8 @@ typedef enum _GOPathAction {
GO_PATH_ACTION_MOVE_TO = 0,
GO_PATH_ACTION_LINE_TO = 1,
GO_PATH_ACTION_CURVE_TO = 2,
- GO_PATH_ACTION_CLOSE_PATH = 3
+ GO_PATH_ACTION_CLOSE_PATH = 3,
+ GO_PATH_ACTION_CHANGE_STATE
} GOPathAction;
static int action_n_args[4] = { 1, 1, 3, 0};
@@ -755,3 +764,498 @@ GOPath *go_path_append (GOPath *path1, GOPath const *path2)
(GOPathClosePathFunc) go_path_append_close, path1);
return path1;
}
+
+/******************************************************************************/
+struct PathScaleClosure {
+ GOPath *path;
+ double scale_x, scale_y;
+};
+
+static void
+go_path_scale_move_to (struct PathScaleClosure *closure,
+ GOPathPoint const *point)
+{
+ go_path_move_to (closure->path,
+ point->x * closure->scale_x,
+ point->y * closure->scale_y);
+}
+
+static void
+go_path_scale_line_to (struct PathScaleClosure *closure,
+ GOPathPoint const *point)
+{
+ go_path_line_to (closure->path,
+ point->x * closure->scale_x,
+ point->y * closure->scale_y);
+}
+
+static void
+go_path_scale_curve_to (struct PathScaleClosure *closure,
+ GOPathPoint const *point0,
+ GOPathPoint const *point1,
+ GOPathPoint const *point2)
+{
+ go_path_curve_to (closure->path,
+ point0->x * closure->scale_x,
+ point0->y * closure->scale_y,
+ point1->x * closure->scale_x,
+ point1->y * closure->scale_y,
+ point2->x * closure->scale_x,
+ point2->y * closure->scale_y);
+}
+
+static void
+go_path_scale_close (struct PathScaleClosure *closure)
+{
+ go_path_close (closure->path);
+}
+
+/**
+ * go_path_scale:
+ * @path: #GOPath
+ * @scale_x: horizontal scale.
+ * @scale_y: vertical scale.
+ *
+ * Builds a scaled.
+ * Returns: (transfer full): the scaled path.
+ **/
+GOPath *
+go_path_scale (GOPath *path, double scale_x, double scale_y)
+{
+ struct PathScaleClosure closure;
+ closure.path = go_path_new ();
+ closure.scale_x = scale_x;
+ closure.scale_y = scale_y;
+ go_path_interpret (path, GO_PATH_DIRECTION_FORWARD,
+ (GOPathMoveToFunc) go_path_scale_move_to,
+ (GOPathLineToFunc) go_path_scale_line_to,
+ (GOPathCurveToFunc) go_path_scale_curve_to,
+ (GOPathClosePathFunc) go_path_scale_close, &closure);
+ return closure.path;
+}
+
+/******************************************************************************/
+
+char *
+go_path_to_svg (GOPath *path)
+{
+ return NULL; /* FIXME */
+}
+
+/*******************************************************************************
+ * Paths from string
+ ******************************************************************************/
+
+static void
+skip_spaces (char **src)
+{
+ while (**src == ' ')
+ (*src)++;
+}
+
+static void
+skip_comma_and_spaces (char **src)
+{
+ while (**src == ' ' || **src == ',')
+ (*src)++;
+}
+
+static gboolean
+parse_value (char **src, double *x)
+{
+ char *end, *c;
+ gboolean integer_part = FALSE;
+ gboolean fractional_part = FALSE;
+ gboolean exponent_part = FALSE;
+ double mantissa = 0.0;
+ double exponent =0.0;
+ double divisor;
+ gboolean mantissa_sign = 1.0;
+ gboolean exponent_sign = 1.0;
+
+ c = *src;
+
+ if (*c == '-') {
+ mantissa_sign = -1.0;
+ c++;
+ } else if (*c == '+')
+ c++;
+
+ if (*c >= '0' && *c <= '9') {
+ integer_part = TRUE;
+ mantissa = *c - '0';
+ c++;
+
+ while (*c >= '0' && *c <= '9') {
+ mantissa = mantissa * 10.0 + *c - '0';
+ c++;
+ }
+ }
+
+
+ if (*c == '.')
+ c++;
+ else if (!integer_part)
+ return FALSE;
+
+ if (*c >= '0' && *c <= '9') {
+ fractional_part = TRUE;
+ mantissa += (*c - '0') * 0.1;
+ divisor = 0.01;
+ c++;
+
+ while (*c >= '0' && *c <= '9') {
+ mantissa += (*c - '0') * divisor;
+ divisor *= 0.1;
+ c++;
+ }
+ }
+
+ if (!fractional_part && !integer_part)
+ return FALSE;
+
+ end = c;
+
+ if (*c == 'E' || *c == 'e') {
+ c++;
+
+ if (*c == '-') {
+ exponent_sign = -1.0;
+ c++;
+ } else if (*c == '+')
+ c++;
+
+ if (*c >= '0' && *c <= '9') {
+ exponent_part = TRUE;
+ exponent = *c - '0';
+ c++;
+
+ while (*c >= '0' && *c <= '9') {
+ exponent = exponent * 10.0 + *c - '0';
+ c++;
+ }
+ }
+
+ }
+
+ if (exponent_part) {
+ end = c;
+ *x = mantissa_sign * mantissa * pow (10.0, exponent_sign * exponent);
+ } else
+ *x = mantissa_sign * mantissa;
+
+ *src = end;
+
+ return TRUE;
+}
+
+static gboolean
+parse_values (char **src, unsigned int n_values, double *values)
+{
+ char *ptr = *src;
+ unsigned int i;
+
+ skip_comma_and_spaces (src);
+
+ for (i = 0; i < n_values; i++) {
+ if (!parse_value (src, &values[i])) {
+ *src = ptr;
+ return FALSE;
+ }
+ skip_comma_and_spaces (src);
+ }
+
+ return TRUE;
+}
+
+static void
+emit_function_2 (char **src, GOPath *path,
+ void (*path_func) (GOPath *, double, double),
+ gboolean relative, double *lastx, double *lasty)
+{
+ double values[2];
+
+ skip_spaces (src);
+
+ while (parse_values (src, 2, values)) {
+ if (relative) {
+ *lastx += values[0];
+ *lasty += values[1];
+ } else {
+ *lastx = values[0];
+ *lasty = values[1];
+ }
+ path_func (path, *lastx, *lasty);
+ }
+}
+
+static void
+emit_function_6 (char **src, GOPath *path,
+ void (*path_func) (GOPath *, double, double, double ,double, double, double),
+ gboolean relative, double *lastx, double *lasty)
+{
+ double values[6];
+
+ skip_spaces (src);
+
+ while (parse_values (src, 6, values)) {
+ if (relative) {
+ values[0] += *lastx;
+ values[1] += *lasty;
+ values[2] += *lastx;
+ values[3] += *lasty;
+ *lastx += values[4];
+ *lasty += values[5];
+ } else {
+ *lastx = values[4];
+ *lasty = values[5];
+ }
+ path_func (path, values[0], values[1], values[2], values[3], *lastx, *lasty);
+ }
+}
+
+static void
+emit_function_8 (char **src, GOPath *path,
+ void (*path_func) (GOPath *, double, double, double ,double, double, double, double ,double),
+ gboolean relative, double *lastx, double *lasty)
+{
+ double values[8];
+
+ skip_spaces (src);
+
+ while (parse_values (src, 8, values)) {
+ if (relative) {
+ values[0] += *lastx;
+ values[1] += *lasty;
+ values[2] += *lastx;
+ values[3] += *lasty;
+ values[4] += *lastx;
+ values[5] += *lasty;
+ *lastx += values[6];
+ *lasty += values[7];
+ } else {
+ *lastx = values[6];
+ *lasty = values[7];
+ }
+ path_func (path, values[0], values[1], values[2], values[3], values[4], values[5], *lastx, *lasty);
+ }
+}
+
+static void
+emit_quadratic (char **src, GOPath *path,
+ gboolean relative, double *lastx, double *lasty)
+{
+ double values[4];
+
+ skip_spaces (src);
+
+ while (parse_values (src, 4, values)) {
+ if (relative) {
+ values[0] += *lastx;
+ values[1] += *lasty;
+ values[2] += *lastx;
+ values[3] += *lasty;
+ }
+ go_path_curve_to (path,
+ (*lastx + 2 * values[0]) / 3.,
+ (*lasty + 2 * values[1]) / 3.,
+ (2 * values[0] + values[2]) / 3.,
+ (2 * values[1] + values[3]) / 3.,
+ values[2], values[3]);
+ *lastx += values[2];
+ *lasty += values[3];
+ }
+}
+
+/**
+ * go_path_new_from_svg:
+ * @src: an SVG path.
+ *
+ * Returns: (transfer full): the newly allocated #GOPath.
+ **/
+GOPath *
+go_path_new_from_svg (char const *src)
+{
+ GOPath *path;
+ char *ptr;
+ double lastx = 0., lasty = 0.;
+
+ if (src == NULL)
+ return NULL;
+
+ path = go_path_new ();
+ ptr = (char *) src;
+
+ skip_spaces (&ptr);
+
+ while (*ptr != '\0') {
+ switch (*ptr) {
+ case 'A':
+ ptr++;
+ break;
+ case 'a':
+ ptr++;
+ break;
+ case 'M':
+ ptr++;
+ emit_function_2 (&ptr, path, go_path_move_to, FALSE, &lastx, &lasty);
+ break;
+ case 'm':
+ ptr++;
+ emit_function_2 (&ptr, path, go_path_move_to, TRUE, &lastx, &lasty);
+ break;
+ case 'H':
+ ptr++;
+ break;
+ case 'h':
+ ptr++;
+ break;
+ case 'L':
+ ptr++;
+ emit_function_2 (&ptr, path, go_path_line_to, FALSE, &lastx, &lasty);
+ break;
+ case 'l':
+ ptr++;
+ emit_function_2 (&ptr, path, go_path_line_to, TRUE, &lastx, &lasty);
+ break;
+ case 'C':
+ ptr++;
+ emit_function_6 (&ptr, path, go_path_curve_to, FALSE, &lastx, &lasty);
+ break;
+ case 'c':
+ ptr++;
+ emit_function_6 (&ptr, path, go_path_curve_to, TRUE, &lastx, &lasty);
+ break;
+ case 'Q':
+ ptr++;
+ emit_quadratic (&ptr, path, FALSE, &lastx, &lasty);
+ break;
+ case 'q':
+ ptr++;
+ emit_quadratic (&ptr, path, TRUE, &lastx, &lasty);
+ break;
+ case 'S':
+ ptr++;
+ break;
+ case 's':
+ ptr++;
+ break;
+ case 'T':
+ ptr++;
+ break;
+ case 't':
+ ptr++;
+ break;
+ case 'V':
+ ptr++;
+ break;
+ case 'v':
+ ptr++;
+ break;
+ case 'Z':
+ case 'z':
+ ptr++;
+ go_path_close (path);
+ break;
+ default:
+ ptr++;
+ break;
+ }
+ }
+ return path;
+}
+
+static void
+go_path_line_arc_to (GOPath *path, double x0, double x1, double x2, double x3,
+ double x4, double x5, double x6, double x7)
+{
+}
+
+static void
+go_path_move_arc_to (GOPath *path, double x0, double x1, double x2, double x3,
+ double x4, double x5, double x6, double x7)
+{
+}
+
+/**
+ * go_path_new_from_odf_enhanced_path:
+ * @src: an ODF enhanced path.
+ *
+ * Returns: (transfer full): the newly alocated #GOPath.
+ **/
+GOPath *
+go_path_new_from_odf_enhanced_path (char const *src, GHashTable const *variables)
+{
+ GOPath *path;
+ char *ptr;
+ double lastx = 0., lasty = 0.;
+
+ if (src == NULL)
+ return NULL;
+
+ path = go_path_new ();
+ ptr = (char *) src;
+
+ skip_spaces (&ptr);
+
+ while (*ptr != '\0') {
+ switch (*ptr) {
+ case 'A':
+ ptr++;
+ emit_function_8 (&ptr, path, go_path_line_arc_to, FALSE, &lastx, &lasty);
+ break;
+ case 'B':
+ ptr++;
+ emit_function_8 (&ptr, path, go_path_move_arc_to, FALSE, &lastx, &lasty);
+ break;
+ case 'C':
+ ptr++;
+ emit_function_6 (&ptr, path, go_path_curve_to, FALSE, &lastx, &lasty);
+ break;
+ case 'F':
+ ptr++;
+ break;
+ case 'L':
+ ptr++;
+ emit_function_2 (&ptr, path, go_path_line_to, FALSE, &lastx, &lasty);
+ break;
+ case 'M':
+ ptr++;
+ emit_function_2 (&ptr, path, go_path_move_to, FALSE, &lastx, &lasty);
+ break;
+ case 'Q':
+ ptr++;
+ emit_quadratic (&ptr, path, FALSE, &lastx, &lasty);
+ break;
+ case 'S':
+ ptr++;
+ break;
+ case 'T':
+ ptr++;
+ break;
+ case 'U':
+ ptr++;
+ break;
+ case 'V':
+ ptr++;
+ break;
+ case 'W':
+ ptr++;
+ break;
+ case 'X':
+ ptr++;
+ break;
+ case 'Y':
+ ptr++;
+ break;
+ case 'Z':
+ ptr++;
+ go_path_close (path);
+ break;
+ default:
+ ptr++;
+ break;
+ }
+}
+ return path;
+}
diff --git a/goffice/utils/go-path.h b/goffice/utils/go-path.h
index 55234c7..8bfc926 100644
--- a/goffice/utils/go-path.h
+++ b/goffice/utils/go-path.h
@@ -37,7 +37,11 @@ G_BEGIN_DECLS
typedef enum {
GO_PATH_DIRECTION_FORWARD,
- GO_PATH_DIRECTION_BACKWARD
+ GO_PATH_DIRECTION_BACKWARD,
+ GO_PATH_DIRECTION_FORWARD_SKIP_NO_FILL,
+ GO_PATH_DIRECTION_BACKWARD_SKIP_NO_FILL,
+ GO_PATH_DIRECTION_FORWARD_SKIP_NO_STROKE,
+ GO_PATH_DIRECTION_BACKWARD_SKIP_NO_STROKE
} GOPathDirection;
typedef enum {
@@ -64,6 +68,8 @@ GType go_path_get_type (void);
#define GO_IS_PATH(x) ((x) != NULL)
GOPath *go_path_new (void);
+GOPath *go_path_new_from_svg (char const *src);
+GOPath *go_path_new_from_odf_enhanced_path (char const *src, GHashTable const *variables);
void go_path_clear (GOPath *path);
GOPath *go_path_ref (GOPath *path);
void go_path_free (GOPath *path);
@@ -110,6 +116,8 @@ void go_path_to_cairo (GOPath const *path,
GOPath *go_path_copy (GOPath const *path);
GOPath *go_path_append (GOPath *path1, GOPath const *path2);
+GOPath *go_path_scale (GOPath *path, double scale_x, double scale_y);
+char *go_path_to_svg (GOPath *path);
G_END_DECLS
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]