[clutter] paint-node: Use JSON-GLib for debug serialization
- From: Emmanuele Bassi <ebassi src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [clutter] paint-node: Use JSON-GLib for debug serialization
- Date: Fri, 16 Mar 2012 12:48:05 +0000 (UTC)
commit f4d8fb054a911aaa69aef9fa40ff4fec4e385b4c
Author: Emmanuele Bassi <ebassi linux intel com>
Date: Fri Feb 3 13:51:29 2012 +0000
paint-node: Use JSON-GLib for debug serialization
Instead of our homegrown string building; this at least ensures that
we're generating proper data, instead of random strings. Plus, using
JsonNode and JsonBuilder, we can ask the PaintNode subclasses to
serialize themselves in a sensible way.
clutter/clutter-paint-node-private.h | 3 +
clutter/clutter-paint-node.c | 201 +++++++++++++++-------------------
clutter/clutter-paint-nodes.c | 83 ++++++++++++++
3 files changed, 175 insertions(+), 112 deletions(-)
---
diff --git a/clutter/clutter-paint-node-private.h b/clutter/clutter-paint-node-private.h
index 346bda8..8e45f34 100644
--- a/clutter/clutter-paint-node-private.h
+++ b/clutter/clutter-paint-node-private.h
@@ -26,6 +26,7 @@
#define __CLUTTER_PAINT_NODE_PRIVATE_H__
#include <glib-object.h>
+#include <json-glib/json-glib.h>
#include <clutter/clutter-paint-node.h>
G_BEGIN_DECLS
@@ -65,6 +66,8 @@ struct _ClutterPaintNodeClass
gboolean (* pre_draw) (ClutterPaintNode *node);
void (* draw) (ClutterPaintNode *node);
void (* post_draw) (ClutterPaintNode *node);
+
+ JsonNode*(* serialize) (ClutterPaintNode *node);
};
typedef enum {
diff --git a/clutter/clutter-paint-node.c b/clutter/clutter-paint-node.c
index dc11191..a56f330 100644
--- a/clutter/clutter-paint-node.c
+++ b/clutter/clutter-paint-node.c
@@ -70,6 +70,7 @@
#include <pango/pango.h>
#include <cogl/cogl.h>
+#include <json-glib/json-glib.h>
#include "clutter-paint-node-private.h"
@@ -778,47 +779,6 @@ clutter_paint_operation_clear (ClutterPaintOperation *op)
}
}
-static void
-clutter_paint_operation_to_string (const ClutterPaintOperation *op,
- GString *buf,
- int level)
-{
- int i;
-
- for (i = 0; i < level; i++)
- g_string_append (buf, " ");
-
- g_string_append (buf, "{ ");
-
- switch (op->opcode)
- {
- case PAINT_OP_INVALID:
- break;
-
- case PAINT_OP_TEX_RECT:
- g_string_append_printf (buf, "\"texrect\" : [ %.2f, %.2f, %.2f, %.2f, %.2f, %.2f, %.2f, %.2f ]",
- op->op.texrect[0],
- op->op.texrect[1],
- op->op.texrect[2],
- op->op.texrect[3],
- op->op.texrect[4],
- op->op.texrect[5],
- op->op.texrect[6],
- op->op.texrect[7]);
- break;
-
- case PAINT_OP_PATH:
- g_string_append_printf (buf, "\"path\" : \"0x%p\"", op->op.path);
- break;
-
- case PAINT_OP_PRIMITIVE:
- g_string_append_printf (buf, "\"primitive\" : \"0x%p\"", op->op.primitive);
- break;
- }
-
- g_string_append (buf, " }");
-}
-
static inline void
clutter_paint_op_init_tex_rect (ClutterPaintOperation *op,
const ClutterActorBox *rect,
@@ -1016,113 +976,130 @@ _clutter_paint_node_paint (ClutterPaintNode *node)
}
}
-static void
-clutter_paint_node_to_string (ClutterPaintNode *node,
- GString *buf,
- int level)
+#ifdef CLUTTER_ENABLE_DEBUG
+static JsonNode *
+clutter_paint_node_serialize (ClutterPaintNode *node)
{
- ClutterPaintNode *iter;
- int i;
+ ClutterPaintNodeClass *klass = CLUTTER_PAINT_NODE_GET_CLASS (node);
- for (i = 0; i < level; i++)
- g_string_append (buf, " ");
+ if (klass->serialize != NULL)
+ return klass->serialize (node);
- g_string_append_c (buf, '"');
- g_string_append (buf, g_type_name (G_TYPE_FROM_INSTANCE (node)));
- g_string_append_c (buf, '"');
+ return json_node_new (JSON_NODE_NULL);
+}
- g_string_append (buf, " : {\n");
+static JsonNode *
+clutter_paint_node_to_json (ClutterPaintNode *node)
+{
+ JsonBuilder *builder;
+ JsonNode *res;
- if (node->name != NULL)
- {
- for (i = 0; i < level + 1; i++)
- g_string_append (buf, " ");
+ builder = json_builder_new ();
- g_string_append_printf (buf, "\"name\" : \"%s\"", node->name);
+ json_builder_begin_object (builder);
- if (node->operations != NULL ||
- node->first_child != NULL)
- g_string_append_c (buf, ',');
+ json_builder_set_member_name (builder, "type");
+ json_builder_add_string_value (builder, g_type_name (G_TYPE_FROM_INSTANCE (node)));
- g_string_append_c (buf, '\n');
- }
+ json_builder_set_member_name (builder, "name");
+ json_builder_add_string_value (builder, node->name);
- if (node->operations != NULL)
- {
- guint o;
+ json_builder_set_member_name (builder, "node-data");
+ json_builder_add_value (builder, clutter_paint_node_serialize (node));
- for (i = 0; i < level + 1; i++)
- g_string_append (buf, " ");
+ json_builder_set_member_name (builder, "operations");
+ json_builder_begin_array (builder);
- g_string_append (buf, "\"operations\" : [\n");
+ if (node->operations != NULL)
+ {
+ guint i;
- for (o = 0; o < node->operations->len; o++)
+ for (i = 0; i < node->operations->len; i++)
{
const ClutterPaintOperation *op;
- op = &g_array_index (node->operations, ClutterPaintOperation, o);
- clutter_paint_operation_to_string (op, buf, level + 2);
-
- if ((o + 1) != node->operations->len)
- g_string_append_c (buf, ',');
-
- g_string_append_c (buf, '\n');
+ op = &g_array_index (node->operations, ClutterPaintOperation, i);
+ json_builder_begin_object (builder);
+
+ switch (op->opcode)
+ {
+ case PAINT_OP_TEX_RECT:
+ json_builder_set_member_name (builder, "texrect");
+ json_builder_begin_array (builder);
+ json_builder_add_double_value (builder, op->op.texrect[0]);
+ json_builder_add_double_value (builder, op->op.texrect[1]);
+ json_builder_add_double_value (builder, op->op.texrect[2]);
+ json_builder_add_double_value (builder, op->op.texrect[3]);
+ json_builder_add_double_value (builder, op->op.texrect[4]);
+ json_builder_add_double_value (builder, op->op.texrect[5]);
+ json_builder_add_double_value (builder, op->op.texrect[6]);
+ json_builder_add_double_value (builder, op->op.texrect[7]);
+ json_builder_end_array (builder);
+ break;
+
+ case PAINT_OP_PATH:
+ json_builder_set_member_name (builder, "path");
+ json_builder_add_int_value (builder, (gint64) op->op.path);
+ break;
+
+ case PAINT_OP_PRIMITIVE:
+ json_builder_set_member_name (builder, "primitive");
+ json_builder_add_int_value (builder, (gint64) op->op.primitive);
+ break;
+
+ case PAINT_OP_INVALID:
+ break;
+ }
+
+ json_builder_end_object (builder);
}
-
- for (i = 0; i < level + 1; i++)
- g_string_append (buf, " ");
-
- g_string_append (buf, "]");
-
- if (node->first_child != NULL)
- g_string_append_c (buf, ',');
-
- g_string_append_c (buf, '\n');
}
- if (node->first_child == NULL)
- goto out;
+ json_builder_end_array (builder);
- for (i = 0; i < level + 1; i++)
- g_string_append (buf, " ");
+ json_builder_set_member_name (builder, "children");
+ json_builder_begin_array (builder);
- g_string_append (buf, "\"children\" : [\n");
-
- for (iter = node->first_child;
- iter != NULL;
- iter = iter->next_sibling)
+ if (node->first_child != NULL)
{
- clutter_paint_node_to_string (iter, buf, level + 2);
+ ClutterPaintNode *child;
+
+ for (child = node->first_child;
+ child != NULL;
+ child = child->next_sibling)
+ {
+ JsonNode *n = clutter_paint_node_to_json (child);
- if (iter->next_sibling != NULL)
- g_string_append (buf, ",\n");
- else
- g_string_append (buf, "\n");
+ json_builder_add_value (builder, n);
+ }
}
- for (i = 0; i < level + 1; i++)
- g_string_append (buf, " ");
+ json_builder_end_array (builder);
+
+ json_builder_end_object (builder);
- g_string_append (buf, "]\n");
+ res = json_builder_get_root (builder);
-out:
- for (i = 0; i < level; i++)
- g_string_append (buf, " ");
+ g_object_unref (builder);
- g_string_append (buf, "}");
+ return res;
}
+#endif /* CLUTTER_ENABLE_DEBUG */
void
_clutter_paint_node_dump_tree (ClutterPaintNode *node)
{
#ifdef CLUTTER_ENABLE_DEBUG
- GString *buf = g_string_sized_new (1024);
+ JsonGenerator *gen = json_generator_new ();
+ char *str;
+ gsize len;
- clutter_paint_node_to_string (node, buf, 0);
+ json_generator_set_root (gen, clutter_paint_node_to_json (node));
+ str = json_generator_to_data (gen, &len);
- CLUTTER_NOTE (PAINT, "Render tree:\n%s", buf->str);
+ g_print ("Render tree starting from %p:\n%s\n", node, str);
- g_string_free (buf, TRUE);
+ g_free (str);
#endif /* CLUTTER_ENABLE_DEBUG */
}
diff --git a/clutter/clutter-paint-nodes.c b/clutter/clutter-paint-nodes.c
index c0868b3..4a4a6c3 100644
--- a/clutter/clutter-paint-nodes.c
+++ b/clutter/clutter-paint-nodes.c
@@ -398,6 +398,46 @@ clutter_pipeline_node_post_draw (ClutterPaintNode *node)
cogl_pop_source ();
}
+static JsonNode *
+clutter_pipeline_node_serialize (ClutterPaintNode *node)
+{
+ ClutterPipelineNode *pnode = CLUTTER_PIPELINE_NODE (node);
+ JsonBuilder *builder;
+ CoglColor color;
+ JsonNode *res;
+
+ if (pnode->pipeline == NULL)
+ return json_node_new (JSON_NODE_NULL);
+
+ builder = json_builder_new ();
+ json_builder_begin_object (builder);
+
+ cogl_pipeline_get_color (pnode->pipeline, &color);
+ json_builder_set_member_name (builder, "color");
+ json_builder_begin_array (builder);
+ json_builder_add_double_value (builder, cogl_color_get_red (&color));
+ json_builder_add_double_value (builder, cogl_color_get_green (&color));
+ json_builder_add_double_value (builder, cogl_color_get_blue (&color));
+ json_builder_add_double_value (builder, cogl_color_get_alpha (&color));
+ json_builder_end_array (builder);
+
+#if 0
+ json_builder_set_member_name (builder, "layers");
+ json_builder_begin_array (builder);
+ cogl_pipeline_foreach_layer (pnode->pipeline,
+ clutter_pipeline_node_serialize_layer,
+ builder);
+ json_builder_end_array (builder);
+#endif
+
+ json_builder_end_object (builder);
+
+ res = json_builder_get_root (builder);
+ g_object_unref (builder);
+
+ return res;
+}
+
static void
clutter_pipeline_node_class_init (ClutterPipelineNodeClass *klass)
{
@@ -408,6 +448,7 @@ clutter_pipeline_node_class_init (ClutterPipelineNodeClass *klass)
node_class->draw = clutter_pipeline_node_draw;
node_class->post_draw = clutter_pipeline_node_post_draw;
node_class->finalize = clutter_pipeline_node_finalize;
+ node_class->serialize = clutter_pipeline_node_serialize;
}
static void
@@ -714,6 +755,47 @@ clutter_text_node_draw (ClutterPaintNode *node)
}
}
+static JsonNode *
+clutter_text_node_serialize (ClutterPaintNode *node)
+{
+ ClutterTextNode *tnode = CLUTTER_TEXT_NODE (node);
+ JsonBuilder *builder;
+ JsonNode *res;
+
+ builder = json_builder_new ();
+
+ json_builder_begin_object (builder);
+
+ json_builder_set_member_name (builder, "layout");
+
+ if (pango_layout_get_character_count (tnode->layout) > 12)
+ {
+ const char *text = pango_layout_get_text (tnode->layout);
+ char *str;
+
+ str = g_strndup (text, 12);
+ json_builder_add_string_value (builder, str);
+ g_free (str);
+ }
+ else
+ json_builder_add_string_value (builder, pango_layout_get_text (tnode->layout));
+
+ json_builder_set_member_name (builder, "color");
+ json_builder_begin_array (builder);
+ json_builder_add_double_value (builder, cogl_color_get_red (&tnode->color));
+ json_builder_add_double_value (builder, cogl_color_get_green (&tnode->color));
+ json_builder_add_double_value (builder, cogl_color_get_blue (&tnode->color));
+ json_builder_add_double_value (builder, cogl_color_get_alpha (&tnode->color));
+ json_builder_end_array (builder);
+
+ json_builder_end_object (builder);
+
+ res = json_builder_get_root (builder);
+ g_object_unref (builder);
+
+ return res;
+}
+
static void
clutter_text_node_class_init (ClutterTextNodeClass *klass)
{
@@ -722,6 +804,7 @@ clutter_text_node_class_init (ClutterTextNodeClass *klass)
node_class->pre_draw = clutter_text_node_pre_draw;
node_class->draw = clutter_text_node_draw;
node_class->finalize = clutter_text_node_finalize;
+ node_class->serialize = clutter_text_node_serialize;
}
static void
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]