Track: Add convenience methods for creating a raw Audio or Video track.
[platform/upstream/gstreamer.git] / ges / ges-track.c
1 /* GStreamer Editing Services
2  * Copyright (C) 2009 Edward Hervey <bilboed@bilboed.com>
3  *
4  * This library is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU Library General Public
6  * License as published by the Free Software Foundation; either
7  * version 2 of the License, or (at your option) any later version.
8  *
9  * This library is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
12  * Library General Public License for more details.
13  *
14  * You should have received a copy of the GNU Library General Public
15  * License along with this library; if not, write to the
16  * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
17  * Boston, MA 02111-1307, USA.
18  */
19
20 #include "ges-internal.h"
21 #include "ges-track.h"
22 #include "ges-track-object.h"
23
24 /**
25  * GESTrack
26  *
27  * Corresponds to one output format (i.e. audio OR video)
28  *
29  * Contains the compatible TrackObject(s)
30  */
31
32 G_DEFINE_TYPE (GESTrack, ges_track, GST_TYPE_BIN);
33
34 enum
35 {
36   ARG_0,
37   ARG_CAPS
38 };
39
40 static void
41 ges_track_get_property (GObject * object, guint property_id,
42     GValue * value, GParamSpec * pspec)
43 {
44   GESTrack *track = GES_TRACK (object);
45
46   switch (property_id) {
47     case ARG_CAPS:
48       gst_value_set_caps (value, track->caps);
49       break;
50     default:
51       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
52   }
53 }
54
55 static void
56 ges_track_set_property (GObject * object, guint property_id,
57     const GValue * value, GParamSpec * pspec)
58 {
59   GESTrack *track = GES_TRACK (object);
60
61   switch (property_id) {
62     case ARG_CAPS:
63       ges_track_set_caps (track, gst_value_get_caps (value));
64       break;
65     default:
66       G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
67   }
68 }
69
70 static void
71 ges_track_dispose (GObject * object)
72 {
73   GESTrack *track = (GESTrack *) object;
74
75   /* FIXME : Remove all TrackObjects ! */
76
77   if (track->composition) {
78     gst_bin_remove (GST_BIN (object), track->composition);
79     track->composition = NULL;
80   }
81
82   G_OBJECT_CLASS (ges_track_parent_class)->dispose (object);
83 }
84
85 static void
86 ges_track_finalize (GObject * object)
87 {
88   G_OBJECT_CLASS (ges_track_parent_class)->finalize (object);
89 }
90
91 static void
92 ges_track_class_init (GESTrackClass * klass)
93 {
94   GObjectClass *object_class = G_OBJECT_CLASS (klass);
95
96   object_class->get_property = ges_track_get_property;
97   object_class->set_property = ges_track_set_property;
98   object_class->dispose = ges_track_dispose;
99   object_class->finalize = ges_track_finalize;
100
101   g_object_class_install_property (object_class, ARG_CAPS,
102       g_param_spec_boxed ("caps", "Caps",
103           "Caps used to filter/choose the output stream",
104           GST_TYPE_CAPS, G_PARAM_READWRITE | G_PARAM_CONSTRUCT));
105 }
106
107 static void
108 ges_track_init (GESTrack * self)
109 {
110   self->composition = gst_element_factory_make ("gnlcomposition", NULL);
111
112   if (!gst_bin_add (GST_BIN (self), self->composition))
113     GST_ERROR ("Couldn't add composition to bin !");
114 }
115
116 GESTrack *
117 ges_track_new (GstCaps * caps)
118 {
119   return g_object_new (GES_TYPE_TRACK, "caps", caps, NULL);
120 }
121
122 GESTrack *
123 ges_track_video_raw_new ()
124 {
125   GESTrack *track;
126   GstCaps *caps = gst_caps_from_string ("video/x-raw-yuv;video/x-raw-rgb");
127
128   track = ges_track_new (caps);
129   gst_caps_unref (caps);
130
131   return track;
132 }
133
134 GESTrack *
135 ges_track_audio_raw_new ()
136 {
137   GESTrack *track;
138   GstCaps *caps = gst_caps_from_string ("audio/x-raw-int;audio/x-raw-float");
139
140   track = ges_track_new (caps);
141   gst_caps_unref (caps);
142
143   return track;
144 }
145
146 void
147 ges_track_set_timeline (GESTrack * track, GESTimeline * timeline)
148 {
149   GST_DEBUG ("track:%p, timeline:%p", track, timeline);
150
151   track->timeline = timeline;
152 }
153
154 void
155 ges_track_set_caps (GESTrack * track, const GstCaps * caps)
156 {
157   GST_DEBUG ("track:%p, caps:%" GST_PTR_FORMAT, track, caps);
158
159   g_return_if_fail (GST_IS_CAPS (caps));
160
161   if (track->caps)
162     gst_caps_unref (track->caps);
163   track->caps = gst_caps_copy (caps);
164
165   /* FIXME : update all trackobjects ? */
166 }
167
168 gboolean
169 ges_track_add_object (GESTrack * track, GESTrackObject * object)
170 {
171   GST_DEBUG ("track:%p, object:%p", track, object);
172
173   if (G_UNLIKELY (object->track != NULL)) {
174     GST_WARNING ("Object already belongs to another track");
175     return FALSE;
176   }
177
178   if (G_UNLIKELY (object->gnlobject != NULL)) {
179     GST_ERROR ("TrackObject doesn't have a gnlobject !");
180     return FALSE;
181   }
182
183   if (G_UNLIKELY (!ges_track_object_set_track (object, track))) {
184     GST_ERROR ("Couldn't properly add the object to the Track");
185     return FALSE;
186   }
187
188   GST_DEBUG ("Adding object to ourself");
189
190   /* make sure the object has a valid gnlobject ! */
191   if (G_UNLIKELY (!gst_bin_add (GST_BIN (track->composition),
192               object->gnlobject))) {
193     GST_WARNING ("Couldn't add object to the GnlComposition");
194     return FALSE;
195   }
196
197   return TRUE;
198 }
199
200 gboolean
201 ges_track_remove_object (GESTrack * track, GESTrackObject * object)
202 {
203   GST_DEBUG ("track:%p, object:%p", track, object);
204
205   if (G_UNLIKELY (object->track != track)) {
206     GST_WARNING ("Object belongs to another track");
207     return FALSE;
208   }
209
210   if (G_LIKELY (object->gnlobject != NULL)) {
211     GST_DEBUG ("Removing GnlObject from composition");
212     if (!gst_bin_remove (GST_BIN (track->composition), object->gnlobject)) {
213       GST_WARNING ("Failed to remove gnlobject from composition");
214       return FALSE;
215     }
216   }
217
218   ges_track_object_set_track (object, NULL);
219
220   return TRUE;
221 }