GESTimelineObject: Subclass from GInitiallyUnowned
authorEdward Hervey <edward.hervey@collabora.co.uk>
Mon, 20 Dec 2010 11:01:04 +0000 (12:01 +0100)
committerEdward Hervey <edward.hervey@collabora.co.uk>
Mon, 20 Dec 2010 11:03:48 +0000 (12:03 +0100)
The floating reference will be owned by the Layer

ges/ges-timeline-layer.c
ges/ges-timeline-object.c
ges/ges-timeline-object.h
tests/check/ges/basic.c
tests/check/ges/layer.c

index ce8249a8e714d26067e6a612831fce1be1be0f0e..05e58e1a8a0153a7ace3ea1b6dfb35d98fae5c6e 100644 (file)
@@ -212,13 +212,15 @@ objects_start_compare (GESTimelineObject * a, GESTimelineObject * b)
 /**
  * ges_timeline_layer_add_object:
  * @layer: a #GESTimelineLayer
- * @object: the #GESTimelineObject to add.
+ * @object: (transfer full): the #GESTimelineObject to add.
  *
- * Adds the object to the layer. The layer will steal a reference to the
- * provided object.
+ * Adds the given object to the layer. Sets the object's parent, and thus
+ * takes ownership of the object.
+ *
+ * An object can only be added to one layer.
  *
  * Returns: TRUE if the object was properly added to the layer, or FALSE
- * if the @layer refused to add the object.
+ * if the @layer refuses to add the object.
  */
 
 gboolean
@@ -230,12 +232,15 @@ ges_timeline_layer_add_object (GESTimelineLayer * layer,
   GST_DEBUG ("layer:%p, object:%p", layer, object);
 
   tl_obj_layer = ges_timeline_object_get_layer (object);
+
   if (G_UNLIKELY (tl_obj_layer)) {
     GST_WARNING ("TimelineObject %p already belongs to another layer");
     g_object_unref (tl_obj_layer);
     return FALSE;
   }
 
+  g_object_ref_sink (object);
+
   /* Take a reference to the object and store it stored by start/priority */
   layer->priv->objects_start =
       g_slist_insert_sorted (layer->priv->objects_start, object,
@@ -268,18 +273,23 @@ ges_timeline_layer_add_object (GESTimelineLayer * layer,
  * @layer: a #GESTimelineLayer
  * @object: the #GESTimelineObject to remove
  *
- * Removes the given @object from the @layer. The reference stolen by the @layer
- * when the object was added will be removed. If you wish to use the object after
- * this function, make sure you take an extra reference to the object before
- * calling this function.
+ * Removes the given @object from the @layer and unparents it.
+ * Unparenting it means the reference owned by @layer on the @object will be
+ * removed. If you wish to use the @object after this function, make sure you
+ * call g_object_ref() before removing it from the @layer.
  *
- * Returns: TRUE if the object was properly remove, else FALSE.
+ * Returns: TRUE if the object could be removed, FALSE if the layer does
+ * not want to remove the object.
  */
 gboolean
 ges_timeline_layer_remove_object (GESTimelineLayer * layer,
     GESTimelineObject * object)
 {
   GESTimelineLayer *tl_obj_layer;
+
+  g_return_val_if_fail (GES_IS_TIMELINE_LAYER (layer), FALSE);
+  g_return_val_if_fail (GES_IS_TIMELINE_OBJECT (object), FALSE);
+
   GST_DEBUG ("layer:%p, object:%p", layer, object);
 
   tl_obj_layer = ges_timeline_object_get_layer (object);
index 4646954f4cc467222b3e4148c317ebfa55df4633..9283eb4ba464f009d4c22c066b82ccdeab446379 100644 (file)
@@ -54,7 +54,8 @@ static void
 track_object_priority_changed_cb (GESTrackObject * child,
     GParamSpec * arg G_GNUC_UNUSED, GESTimelineObject * object);
 
-G_DEFINE_ABSTRACT_TYPE (GESTimelineObject, ges_timeline_object, G_TYPE_OBJECT);
+G_DEFINE_ABSTRACT_TYPE (GESTimelineObject, ges_timeline_object,
+    G_TYPE_INITIALLY_UNOWNED);
 
 /* Mapping of relationship between a TimelineObject and the TrackObjects
  * it controls
index a82f65713c960020cf89f07cebb11611ccb6b573..b76c4fded420c1d4a507b10d92f7803494c80782 100644 (file)
@@ -156,7 +156,7 @@ typedef gboolean (*GESCreateTrackObjectsFunc) (GESTimelineObject * object,
  */
 struct _GESTimelineObject {
   /*< private >*/
-  GObject parent;
+  GInitiallyUnowned parent;
 
   GESTimelineObjectPrivate *priv;
   
@@ -186,7 +186,7 @@ struct _GESTimelineObject {
  */
 struct _GESTimelineObjectClass {
   /*< private >*/
-  GObjectClass parent_class;
+  GInitiallyUnownedClass parent_class;
 
   /*< public >*/
   GESCreateTrackObjectFunc create_track_object;
index b0f53b850c2b551da60fbbed0538c7aad7c07383..0c72f1987c34125813274498c6420491b311b93b 100644 (file)
@@ -93,11 +93,15 @@ GST_START_TEST (test_ges_scenario)
   source = ges_custom_timeline_source_new (my_fill_track_func, NULL);
   fail_unless (source != NULL);
 
+  /* The source will be floating before added to the layer... */
+  fail_unless (g_object_is_floating (source));
   GST_DEBUG ("Adding the source to the timeline layer");
   fail_unless (ges_timeline_layer_add_object (layer,
           GES_TIMELINE_OBJECT (source)));
+  fail_if (g_object_is_floating (source));
   tmp_layer = ges_timeline_object_get_layer (GES_TIMELINE_OBJECT (source));
   fail_unless (tmp_layer == layer);
+  /* The timeline stole our reference */
   ASSERT_OBJECT_REFCOUNT (source, "source", 1);
   g_object_unref (tmp_layer);
   ASSERT_OBJECT_REFCOUNT (layer, "layer", 1);
index 7fbcb7549f4c2a474216998a319f274e797a54ed..5e3ec09d81a4a35e9c635bd033b6f16a0f1f3e3a 100644 (file)
@@ -97,8 +97,10 @@ GST_START_TEST (test_layer_properties)
   assert_equals_uint64 (GES_TIMELINE_OBJECT_PRIORITY (object), 0);
 
   /* Add the object to the timeline */
+  fail_unless (g_object_is_floating (object));
   fail_unless (ges_timeline_layer_add_object (layer,
           GES_TIMELINE_OBJECT (object)));
+  fail_if (g_object_is_floating (object));
   trackobject = ges_timeline_object_find_track_object (object, track,
       G_TYPE_NONE);
   fail_unless (trackobject != NULL);