[gnome-photos] pipeline: Mark nodes as passthrough instead of actually removing them



commit 155d1df7ab43f0ca64c090390177ae6adcdc3054
Author: Debarshi Ray <debarshir gnome org>
Date:   Fri Apr 8 19:25:32 2016 +0200

    pipeline: Mark nodes as passthrough instead of actually removing them
    
    The strategy of removing a GeglNode from the graph when it is no
    longer needed doesn't match with our desire to have pre-determined
    positions for certain operations. It will be easier if we can mark
    certain nodes as unused without removing or changing their position
    in the graph. In fact, right now, we ensure that photos:insta-filter is
    the first operation in the pipeline by creating it before any other
    operation is added, and hide its existence by setting it to its NONE
    preset. When photos:insta-filter is actually asked for, we update the
    properties of this node. We want to extend this technique to cover
    other nodes as well.
    
    Unfortunately, simply adding a GeglNode and setting it to its no-op
    values is not ideal. It will confuse photos_pipeline_get. It won't be
    able to distinguish between no-op values actually set by the user, and
    those that were set internally to mimic a removal. To be fair, it is
    not clear whether that matters, though. More importantly, tracking the
    no-op values can be tricky in practice. We can assume the default
    values of the properties represent the no-op state. However, a quick
    look at the generated XML won't tell us which nodes are no-ops, unless
    we remember the set values, which is hard.
    
    One option is to set GeglNode:name to gegl:nop when we want to remove
    it. This is almost perfect - we can check the name in
    photos_pipeline_get to know if an operation is meant to be absent, and
    they will stand out in the XML. However, this won't work because
    gegl:nop nodes are skipped during serialization. This means that when
    the graph is deserialized, the gegl:nop nodes will be missing and it
    will defeat our whole strategy.
    
    Instead, we can mark them as passthrough nodes. They have the same
    effect as gegl:nop with the benefit that they are not skipped during
    serialization.
    
    https://bugzilla.gnome.org/show_bug.cgi?id=764801

 src/photos-pipeline.c |   28 ++++++++++++----------------
 1 files changed, 12 insertions(+), 16 deletions(-)
---
diff --git a/src/photos-pipeline.c b/src/photos-pipeline.c
index dc634d2..d5558ff 100644
--- a/src/photos-pipeline.c
+++ b/src/photos-pipeline.c
@@ -76,10 +76,8 @@ photos_pipeline_reset (PhotosPipeline *self)
   last = gegl_node_get_producer (output, "input", NULL);
   g_return_if_fail (last == input);
 
-  node = gegl_node_new_child (self->graph,
-                              "operation", "photos:insta-filter",
-                              "preset", PHOTOS_OPERATION_INSTA_PRESET_NONE,
-                              NULL);
+  node = gegl_node_new_child (self->graph, "operation", "photos:insta-filter", NULL);
+  gegl_node_set_passthrough (node, TRUE);
   gegl_node_link_many (input, node, output, NULL);
   g_hash_table_insert (self->hash, g_strdup ("photos:insta-filter"), g_object_ref (node));
 }
@@ -450,6 +448,10 @@ photos_pipeline_add (PhotosPipeline *self, const gchar *operation, const gchar *
       gegl_node_link_many (last, node, output, NULL);
       g_hash_table_insert (self->hash, g_strdup (operation), g_object_ref (node));
     }
+  else
+    {
+      gegl_node_set_passthrough (node, FALSE);
+    }
 
   gegl_node_set_valist (node, first_property_name, ap);
 
@@ -470,6 +472,9 @@ photos_pipeline_get (PhotosPipeline *self, const gchar *operation, const gchar *
   if (node == NULL)
     goto out;
 
+  if (gegl_node_get_passthrough (node))
+    goto out;
+
   gegl_node_get_valist (node, first_property_name, ap);
   ret_val = TRUE;
 
@@ -604,25 +609,17 @@ gboolean
 photos_pipeline_remove (PhotosPipeline *self, const gchar *operation)
 {
   GeglNode *node;
-  GeglNode *source;
-  GeglNode **sinks = NULL;
   gboolean ret_val = FALSE;
   gchar *xml = NULL;
-  gint i;
-  gint nsinks;
 
   node = GEGL_NODE (g_hash_table_lookup (self->hash, operation));
   if (node == NULL)
     goto out;
 
-  source = gegl_node_get_producer (node, "input", NULL);
-  nsinks = gegl_node_get_consumers (node, "output", &sinks, NULL);
-
-  g_hash_table_remove (self->hash, operation);
-  gegl_node_remove_child (self->graph, node);
+  if (gegl_node_get_passthrough (node))
+    goto out;
 
-  for (i = 0; i < nsinks; i++)
-    gegl_node_link (source, sinks[i]);
+  gegl_node_set_passthrough (node, TRUE);
 
   xml = gegl_node_to_xml_full (self->graph, self->graph, "/");
   photos_debug (PHOTOS_DEBUG_GEGL, "Pipeline: %s", xml);
@@ -630,7 +627,6 @@ photos_pipeline_remove (PhotosPipeline *self, const gchar *operation)
   ret_val = TRUE;
 
  out:
-  g_free (sinks);
   g_free (xml);
   return ret_val;
 }


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