snapshot: Use one GPtrArray for all nodes

Instead of creating one GPtrArray per GtkSnapshotState and saving nodes
in there, create one GPtrArray per snapshot and assign a
start_node_index to every GtkSnapshotState as well as a n_nodes variable
so every state knows which nodes belong to it.
This commit is contained in:
Timm Bäder 2017-10-01 14:28:11 +02:00
parent 8e59b3b387
commit f5297e6f4b
2 changed files with 21 additions and 7 deletions

View File

@ -90,14 +90,14 @@ gtk_snapshot_push_state (GtkSnapshot *snapshot,
g_array_set_size (snapshot->state_stack, snapshot->state_stack->len + 1); g_array_set_size (snapshot->state_stack, snapshot->state_stack->len + 1);
state = &g_array_index (snapshot->state_stack, GtkSnapshotState, snapshot->state_stack->len - 1); state = &g_array_index (snapshot->state_stack, GtkSnapshotState, snapshot->state_stack->len - 1);
state->nodes = g_ptr_array_new_with_free_func ((GDestroyNotify) gsk_render_node_unref);
state->name = name; state->name = name;
if (clip) if (clip)
state->clip_region = cairo_region_reference (clip); state->clip_region = cairo_region_reference (clip);
state->translate_x = translate_x; state->translate_x = translate_x;
state->translate_y = translate_y; state->translate_y = translate_y;
state->collect_func = collect_func; state->collect_func = collect_func;
state->start_node_index = snapshot->nodes->len;
state->n_nodes = 0;
return state; return state;
} }
@ -121,7 +121,6 @@ gtk_snapshot_get_previous_state (const GtkSnapshot *snapshot)
static void static void
gtk_snapshot_state_clear (GtkSnapshotState *state) gtk_snapshot_state_clear (GtkSnapshotState *state)
{ {
g_ptr_array_unref (state->nodes);
g_clear_pointer (&state->clip_region, cairo_region_destroy); g_clear_pointer (&state->clip_region, cairo_region_destroy);
g_clear_pointer (&state->name, g_free); g_clear_pointer (&state->name, g_free);
} }
@ -140,6 +139,7 @@ gtk_snapshot_init (GtkSnapshot *snapshot,
snapshot->renderer = renderer; snapshot->renderer = renderer;
snapshot->state_stack = g_array_new (FALSE, TRUE, sizeof (GtkSnapshotState)); snapshot->state_stack = g_array_new (FALSE, TRUE, sizeof (GtkSnapshotState));
g_array_set_clear_func (snapshot->state_stack, (GDestroyNotify)gtk_snapshot_state_clear); g_array_set_clear_func (snapshot->state_stack, (GDestroyNotify)gtk_snapshot_state_clear);
snapshot->nodes = g_ptr_array_new_with_free_func ((GDestroyNotify)gsk_render_node_unref);
if (name && record_names) if (name && record_names)
{ {
@ -978,10 +978,19 @@ gtk_snapshot_pop_internal (GtkSnapshot *snapshot)
node = state->collect_func (snapshot, node = state->collect_func (snapshot,
state, state,
(GskRenderNode **) state->nodes->pdata, (GskRenderNode **) snapshot->nodes->pdata + state->start_node_index,
state->nodes->len, state->n_nodes,
state->name); state->name);
/* The collect func may not modify the state stack... */
g_assert (state_index == snapshot->state_stack->len - 1);
/* Remove all the state's nodes from the list of nodes */
g_assert (state->start_node_index + state->n_nodes == snapshot->nodes->len);
g_ptr_array_remove_range (snapshot->nodes,
snapshot->nodes->len - state->n_nodes,
state->n_nodes);
g_array_remove_index (snapshot->state_stack, state_index); g_array_remove_index (snapshot->state_stack, state_index);
return node; return node;
@ -1009,6 +1018,7 @@ gtk_snapshot_finish (GtkSnapshot *snapshot)
result = gtk_snapshot_pop_internal (snapshot); result = gtk_snapshot_pop_internal (snapshot);
g_array_free (snapshot->state_stack, TRUE); g_array_free (snapshot->state_stack, TRUE);
g_ptr_array_free (snapshot->nodes, TRUE);
return result; return result;
} }
@ -1118,6 +1128,7 @@ gtk_snapshot_append_node (GtkSnapshot *snapshot,
GskRenderNode *node) GskRenderNode *node)
{ {
GtkSnapshotState *current_state; GtkSnapshotState *current_state;
g_return_if_fail (snapshot != NULL); g_return_if_fail (snapshot != NULL);
g_return_if_fail (GSK_IS_RENDER_NODE (node)); g_return_if_fail (GSK_IS_RENDER_NODE (node));
@ -1125,7 +1136,8 @@ gtk_snapshot_append_node (GtkSnapshot *snapshot,
if (current_state) if (current_state)
{ {
g_ptr_array_add (current_state->nodes, gsk_render_node_ref (node)); g_ptr_array_add (snapshot->nodes, gsk_render_node_ref (node));
current_state->n_nodes ++;
} }
else else
{ {

View File

@ -32,7 +32,8 @@ typedef GskRenderNode * (* GtkSnapshotCollectFunc) (GtkSnapshot *snapshot,
struct _GtkSnapshotState { struct _GtkSnapshotState {
char *name; char *name;
GPtrArray *nodes; guint start_node_index;
guint n_nodes;
cairo_region_t *clip_region; cairo_region_t *clip_region;
int translate_x; int translate_x;
@ -83,6 +84,7 @@ struct _GtkSnapshot {
gboolean record_names; gboolean record_names;
GskRenderer *renderer; GskRenderer *renderer;
GArray *state_stack; GArray *state_stack;
GPtrArray *nodes;
}; };
void gtk_snapshot_init (GtkSnapshot *state, void gtk_snapshot_init (GtkSnapshot *state,