From c90f399bfb7766b7933fc6eb4f96ac2b70a2e339 Mon Sep 17 00:00:00 2001 From: Edward Hervey Date: Mon, 20 Dec 2010 11:56:37 +0100 Subject: [PATCH] TimelineObject: Hold a reference to the controlled TrackObject --- ges/ges-timeline-object.c | 5 +++ tests/check/ges/basic.c | 87 +++++++++++++++++++++++++++++------- tests/check/ges/filesource.c | 15 ++++--- 3 files changed, 86 insertions(+), 21 deletions(-) diff --git a/ges/ges-timeline-object.c b/ges/ges-timeline-object.c index b6446e5ce3..4646954f4c 100644 --- a/ges/ges-timeline-object.c +++ b/ges/ges-timeline-object.c @@ -343,6 +343,8 @@ ges_timeline_object_create_track_objects_func (GESTimelineObject * object, * Add a track object to the timeline object. Should only be called by * subclasses implementing the create_track_objects (plural) vmethod. * + * Takes a reference on @trobj. + * * Returns: %TRUE on success, %FALSE on failure. */ @@ -359,6 +361,7 @@ ges_timeline_object_add_track_object (GESTimelineObject * object, GESTrackObject return FALSE; ges_track_object_set_timeline_object (trobj, object); + g_object_ref (trobj); mapping = g_slice_new0 (ObjectMapping); mapping->object = trobj; @@ -445,6 +448,8 @@ ges_timeline_object_release_track_object (GESTimelineObject * object, ges_track_object_set_timeline_object (trackobject, NULL); + GST_DEBUG ("Removing reference to track object %p", trackobject); + g_object_unref (trackobject); /* FIXME : resync properties ? */ diff --git a/tests/check/ges/basic.c b/tests/check/ges/basic.c index 1ee298d4d7..b0f53b850c 100644 --- a/tests/check/ges/basic.c +++ b/tests/check/ges/basic.c @@ -107,14 +107,22 @@ GST_START_TEST (test_ges_scenario) ges_timeline_object_get_track_objects (GES_TIMELINE_OBJECT (source)); fail_unless (trackobjects != NULL); trackobject = GES_TRACK_OBJECT (trackobjects->data); - ASSERT_OBJECT_REFCOUNT (trackobject, "trackobject", 2); + /* There are 3 references: + * 1 by the timelineobject + * 1 by the track + * 1 added by the call to _get_track_objects() above */ + ASSERT_OBJECT_REFCOUNT (trackobject, "trackobject", 3); for (tmp = trackobjects; tmp; tmp = tmp->next) { g_object_unref (GES_TRACK_OBJECT (tmp->data)); } g_list_free (trackobjects); - ASSERT_OBJECT_REFCOUNT (trackobject, "trackobject", 1); + /* There are 2 references: + * 1 by the timelineobject + * 1 by the track */ + ASSERT_OBJECT_REFCOUNT (trackobject, "trackobject", 2); GST_DEBUG ("Remove the TimelineObject from the layer"); + /* Now remove the timelineobject */ g_object_ref (source); ASSERT_OBJECT_REFCOUNT (layer, "layer", 1); @@ -229,12 +237,19 @@ GST_START_TEST (test_ges_timeline_add_layer) ges_timeline_object_get_track_objects (GES_TIMELINE_OBJECT (s1)); fail_unless (trackobjects != NULL); trackobject = GES_TRACK_OBJECT (trackobjects->data); - ASSERT_OBJECT_REFCOUNT (trackobject, "trackobject", 2); + /* There are 3 references: + * 1 by the timelineobject + * 1 by the trackobject + * 1 added by the call to _get_track_objects() above */ + ASSERT_OBJECT_REFCOUNT (trackobject, "trackobject", 3); for (tmp = trackobjects; tmp; tmp = tmp->next) { g_object_unref (GES_TRACK_OBJECT (tmp->data)); } g_list_free (trackobjects); - ASSERT_OBJECT_REFCOUNT (trackobject, "trackobject", 1); + /* There are 2 references: + * 1 by the timelineobject + * 1 by the trackobject */ + ASSERT_OBJECT_REFCOUNT (trackobject, "trackobject", 2); trackobjects = ges_timeline_object_get_track_objects (GES_TIMELINE_OBJECT (s2)); @@ -244,7 +259,10 @@ GST_START_TEST (test_ges_timeline_add_layer) g_object_unref (GES_TRACK_OBJECT (tmp->data)); } g_list_free (trackobjects); - ASSERT_OBJECT_REFCOUNT (GES_TRACK_OBJECT (trackobject), "trackobject", 1); + /* There are 2 references: + * 1 by the timelineobject + * 1 by the trackobject */ + ASSERT_OBJECT_REFCOUNT (GES_TRACK_OBJECT (trackobject), "trackobject", 2); trackobjects = ges_timeline_object_get_track_objects (GES_TIMELINE_OBJECT (s3)); @@ -254,7 +272,10 @@ GST_START_TEST (test_ges_timeline_add_layer) g_object_unref (GES_TRACK_OBJECT (tmp->data)); } g_list_free (trackobjects); - ASSERT_OBJECT_REFCOUNT (trackobject, "trackobject", 1); + /* There are 2 references: + * 1 by the timelineobject + * 1 by the trackobject */ + ASSERT_OBJECT_REFCOUNT (trackobject, "trackobject", 2); /* theoretically this is all we need to do to ensure cleanup */ g_object_unref (timeline); @@ -330,7 +351,11 @@ GST_START_TEST (test_ges_timeline_add_layer_first) ges_timeline_object_get_track_objects (GES_TIMELINE_OBJECT (s1)); fail_unless (trackobjects != NULL); for (tmp = trackobjects; tmp; tmp = tmp->next) { - ASSERT_OBJECT_REFCOUNT (GES_TRACK_OBJECT (tmp->data), "trackobject", 2); + /* Each object has 3 references: + * 1 by the timelineobject + * 1 by the track + * 1 added by _get_track_object() above */ + ASSERT_OBJECT_REFCOUNT (GES_TRACK_OBJECT (tmp->data), "trackobject", 3); g_object_unref (GES_TRACK_OBJECT (tmp->data)); } g_list_free (trackobjects); @@ -339,7 +364,11 @@ GST_START_TEST (test_ges_timeline_add_layer_first) ges_timeline_object_get_track_objects (GES_TIMELINE_OBJECT (s2)); fail_unless (trackobjects != NULL); for (tmp = trackobjects; tmp; tmp = tmp->next) { - ASSERT_OBJECT_REFCOUNT (GES_TRACK_OBJECT (tmp->data), "trackobject", 2); + /* Each object has 3 references: + * 1 by the timelineobject + * 1 by the track + * 1 added by _get_track_object() above */ + ASSERT_OBJECT_REFCOUNT (GES_TRACK_OBJECT (tmp->data), "trackobject", 3); g_object_unref (GES_TRACK_OBJECT (tmp->data)); } g_list_free (trackobjects); @@ -348,7 +377,11 @@ GST_START_TEST (test_ges_timeline_add_layer_first) ges_timeline_object_get_track_objects (GES_TIMELINE_OBJECT (s3)); fail_unless (trackobjects != NULL); for (tmp = trackobjects; tmp; tmp = tmp->next) { - ASSERT_OBJECT_REFCOUNT (GES_TRACK_OBJECT (tmp->data), "trackobject", 2); + /* Each object has 3 references: + * 1 by the timelineobject + * 1 by the track + * 1 added by _get_track_object() above */ + ASSERT_OBJECT_REFCOUNT (GES_TRACK_OBJECT (tmp->data), "trackobject", 3); g_object_unref (GES_TRACK_OBJECT (tmp->data)); } g_list_free (trackobjects); @@ -426,37 +459,61 @@ GST_START_TEST (test_ges_timeline_remove_track) ges_timeline_object_get_track_objects (GES_TIMELINE_OBJECT (s1)); fail_unless (trackobjects != NULL); t1 = GES_TRACK_OBJECT ((trackobjects)->data); - g_object_ref (t1); for (tmp = trackobjects; tmp; tmp = tmp->next) { + /* There are 3 references held: + * 1 by the timelineobject + * 1 by the track + * 1 added by the call to _get_track_objects() above */ ASSERT_OBJECT_REFCOUNT (GES_TRACK_OBJECT (tmp->data), "trackobject", 3); g_object_unref (GES_TRACK_OBJECT (tmp->data)); } + g_object_ref (t1); g_list_free (trackobjects); - ASSERT_OBJECT_REFCOUNT (t1, "trackobject", 2); + /* There are 3 references held: + * 1 by the timelinobject + * 1 by the track + * 1 added by ourselves above (g_object_ref (t1)) */ + ASSERT_OBJECT_REFCOUNT (t1, "trackobject", 3); trackobjects = ges_timeline_object_get_track_objects (GES_TIMELINE_OBJECT (s2)); fail_unless (trackobjects != NULL); t2 = GES_TRACK_OBJECT (trackobjects->data); - g_object_ref (t2); for (tmp = trackobjects; tmp; tmp = tmp->next) { + /* There are 3 references held: + * 1 by the timelineobject + * 1 by the track + * 1 added by the call to _get_track_objects() above */ ASSERT_OBJECT_REFCOUNT (GES_TRACK_OBJECT (tmp->data), "trackobject", 3); g_object_unref (GES_TRACK_OBJECT (tmp->data)); } + g_object_ref (t2); g_list_free (trackobjects); - ASSERT_OBJECT_REFCOUNT (t2, "t2", 2); + /* There are 3 references held: + * 1 by the timelinobject + * 1 by the track + * 1 added by ourselves above (g_object_ref (t1)) */ + ASSERT_OBJECT_REFCOUNT (t2, "t2", 3); trackobjects = ges_timeline_object_get_track_objects (GES_TIMELINE_OBJECT (s3)); fail_unless (trackobjects != NULL); t3 = GES_TRACK_OBJECT (trackobjects->data); - g_object_ref (t3); for (tmp = trackobjects; tmp; tmp = tmp->next) { + /* There are 3 references held: + * 1 by the timelineobject + * 1 by the track + * 1 added by the call to _get_track_objects() above */ ASSERT_OBJECT_REFCOUNT (GES_TRACK_OBJECT (tmp->data), "trackobject", 3); g_object_unref (GES_TRACK_OBJECT (tmp->data)); } + g_object_ref (t3); g_list_free (trackobjects); - ASSERT_OBJECT_REFCOUNT (t3, "t3", 2); + /* There are 3 references held: + * 1 by the timelinobject + * 1 by the track + * 1 added by ourselves above (g_object_ref (t1)) */ + ASSERT_OBJECT_REFCOUNT (t3, "t3", 3); /* remove the track and check that the track objects have been released */ fail_unless (ges_timeline_remove_track (timeline, track)); diff --git a/tests/check/ges/filesource.c b/tests/check/ges/filesource.c index 1d69faa6c9..e4dbfbc77a 100644 --- a/tests/check/ges/filesource.c +++ b/tests/check/ges/filesource.c @@ -57,8 +57,9 @@ GST_START_TEST (test_filesource_basic) track); fail_unless (trackobject != NULL); - /* The track holds a reference to the object */ - ASSERT_OBJECT_REFCOUNT (trackobject, "Track Object", 1); + /* The track holds a reference to the object + * and the timelineobject holds a reference on the object */ + ASSERT_OBJECT_REFCOUNT (trackobject, "Track Object", 2); fail_unless (ges_timeline_object_release_track_object (GES_TIMELINE_OBJECT (source), trackobject) == TRUE); @@ -175,8 +176,9 @@ GST_START_TEST (test_filesource_images) trobj = ges_timeline_object_create_track_object (tlobj, v); fail_unless (GES_IS_TRACK_IMAGE_SOURCE (trobj)); - /* The track holds a reference to the object */ - ASSERT_OBJECT_REFCOUNT (trobj, "Video Track Object", 1); + /* The track holds a reference to the object + * and the timelinobject holds a reference to the object */ + ASSERT_OBJECT_REFCOUNT (trobj, "Video Track Object", 2); ges_track_remove_object (v, trobj); ges_timeline_object_release_track_object (tlobj, trobj); @@ -187,8 +189,9 @@ GST_START_TEST (test_filesource_images) trobj = ges_timeline_object_create_track_object (tlobj, a); fail_unless (GES_IS_TRACK_AUDIO_TEST_SOURCE (trobj)); - /* The track holds a reference to the object */ - ASSERT_OBJECT_REFCOUNT (trobj, "Audio Track Object", 1); + /* The track holds a reference to the object + * And the timelineobject holds a reference to the object */ + ASSERT_OBJECT_REFCOUNT (trobj, "Audio Track Object", 2); ges_track_remove_object (v, trobj); ges_timeline_object_release_track_object (tlobj, trobj);