GST_STATIC_CAPS ("video/x-theora")
);
-static GstCaps *theora_enc_src_caps;
-
-static void
-_do_init (GType object_type)
-{
- const GInterfaceInfo preset_interface_info = {
- NULL, /* interface_init */
- NULL, /* interface_finalize */
- NULL /* interface_data */
- };
-
- g_type_add_interface_static (object_type, GST_TYPE_PRESET,
- &preset_interface_info);
-}
+#define gst_theora_enc_parent_class parent_class
+G_DEFINE_TYPE_WITH_CODE (GstTheoraEnc, gst_theora_enc,
+ GST_TYPE_ELEMENT, G_IMPLEMENT_INTERFACE (GST_TYPE_PRESET, NULL));
-GST_BOILERPLATE_FULL (GstTheoraEnc, gst_theora_enc, GstElement,
- GST_TYPE_ELEMENT, _do_init);
+static GstCaps *theora_enc_src_caps;
static gboolean theora_enc_sink_event (GstPad * pad, GstEvent * event);
static gboolean theora_enc_src_event (GstPad * pad, GstEvent * event);
static GstFlowReturn theora_enc_chain (GstPad * pad, GstBuffer * buffer);
static GstStateChangeReturn theora_enc_change_state (GstElement * element,
GstStateChange transition);
-static GstCaps *theora_enc_sink_getcaps (GstPad * pad);
+static GstCaps *theora_enc_sink_getcaps (GstPad * pad, GstCaps * filter);
static gboolean theora_enc_sink_setcaps (GstPad * pad, GstCaps * caps);
static void theora_enc_get_property (GObject * object, guint prop_id,
GValue * value, GParamSpec * pspec);
static char *theora_enc_get_supported_formats (void);
static void
-gst_theora_enc_base_init (gpointer g_class)
-{
- GstElementClass *element_class = GST_ELEMENT_CLASS (g_class);
-
- gst_element_class_add_pad_template (element_class,
- gst_static_pad_template_get (&theora_enc_src_factory));
- gst_element_class_add_pad_template (element_class,
- gst_static_pad_template_get (&theora_enc_sink_factory));
- gst_element_class_set_details_simple (element_class,
- "Theora video encoder", "Codec/Encoder/Video",
- "encode raw YUV video to a theora stream",
- "Wim Taymans <wim@fluendo.com>");
-}
-
-static void
gst_theora_enc_class_init (GstTheoraEncClass * klass)
{
GObjectClass *gobject_class = (GObjectClass *) klass;
THEORA_DEF_MULTIPASS_MODE,
(GParamFlags) G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
+ gst_element_class_add_pad_template (gstelement_class,
+ gst_static_pad_template_get (&theora_enc_src_factory));
+ gst_element_class_add_pad_template (gstelement_class,
+ gst_static_pad_template_get (&theora_enc_sink_factory));
+ gst_element_class_set_details_simple (gstelement_class,
+ "Theora video encoder", "Codec/Encoder/Video",
+ "encode raw YUV video to a theora stream",
+ "Wim Taymans <wim@fluendo.com>");
+
caps_string = g_strdup_printf ("video/x-raw-yuv, "
"format = (fourcc) { %s }, "
"framerate = (fraction) [1/MAX, MAX], "
}
static void
-gst_theora_enc_init (GstTheoraEnc * enc, GstTheoraEncClass * g_class)
+gst_theora_enc_init (GstTheoraEnc * enc)
{
enc->sinkpad =
gst_pad_new_from_static_template (&theora_enc_sink_factory, "sink");
}
static GstCaps *
-theora_enc_sink_getcaps (GstPad * pad)
+theora_enc_sink_getcaps (GstPad * pad, GstCaps * filter)
{
GstTheoraEnc *encoder;
GstPad *peer;
GstCaps *caps;
/* If we already have caps return them */
- if (GST_PAD_CAPS (pad))
- return gst_caps_ref (GST_PAD_CAPS (pad));
+ if ((caps = gst_pad_get_current_caps (pad)) != NULL)
+ return caps;
encoder = GST_THEORA_ENC (gst_pad_get_parent (pad));
if (!encoder)
GstStructure *s;
guint i, n;
- peer_caps = gst_pad_get_caps (peer);
+ peer_caps = gst_pad_get_caps (peer, NULL);
/* Translate peercaps to YUV */
peer_caps = gst_caps_make_writable (peer_caps);
gst_object_unref (encoder);
+ if (filter) {
+ GstCaps *intersection;
+
+ intersection =
+ gst_caps_intersect_full (filter, caps, GST_CAPS_INTERSECT_FIRST);
+ gst_caps_unref (caps);
+ caps = intersection;
+ }
+
return caps;
}
goto done;
}
- memcpy (GST_BUFFER_DATA (buf), packet->packet, packet->bytes);
- gst_buffer_set_caps (buf, GST_PAD_CAPS (enc->srcpad));
+ gst_buffer_fill (buf, 0, packet->packet, packet->bytes);
/* see ext/ogg/README; OFFSET_END takes "our" granulepos, OFFSET its
* time representation */
GST_BUFFER_OFFSET_END (buf) =
{
GstFlowReturn ret;
- enc->bytes_out += GST_BUFFER_SIZE (buffer);
+ enc->bytes_out += gst_buffer_get_size (buffer);
ret = gst_pad_push (enc->srcpad, buffer);
enc = GST_THEORA_ENC (GST_PAD_PARENT (pad));
switch (GST_EVENT_TYPE (event)) {
- case GST_EVENT_NEWSEGMENT:
+ case GST_EVENT_SEGMENT:
{
- gboolean update;
- gdouble rate, applied_rate;
- GstFormat format;
- gint64 start, stop, time;
-
- gst_event_parse_new_segment_full (event, &update, &rate, &applied_rate,
- &format, &start, &stop, &time);
-
- gst_segment_set_newsegment_full (&enc->segment, update, rate,
- applied_rate, format, start, stop, time);
+ gst_event_copy_segment (event, &enc->segment);
res = gst_pad_push_event (enc->srcpad, event);
break;
while (!done) {
if (gst_adapter_available (enc->multipass_cache_adapter) == 0) {
+ guint8 *data;
+ gsize size;
+
cache_buf = gst_buffer_new_and_alloc (512);
+
+ data = gst_buffer_map (cache_buf, &size, NULL, GST_MAP_READ);
stat = g_io_channel_read_chars (enc->multipass_cache_fd,
- (gchar *) GST_BUFFER_DATA (cache_buf), GST_BUFFER_SIZE (cache_buf),
- &bytes_read, NULL);
+ (gchar *) data, size, &bytes_read, NULL);
if (bytes_read <= 0) {
+ gst_buffer_unmap (cache_buf, data, 0);
gst_buffer_unref (cache_buf);
break;
} else {
- GST_BUFFER_SIZE (cache_buf) = bytes_read;
-
+ gst_buffer_unmap (cache_buf, data, bytes_read);
gst_adapter_push (enc->multipass_cache_adapter, cache_buf);
}
}
bytes_read =
MIN (gst_adapter_available (enc->multipass_cache_adapter), 512);
- cache_data = gst_adapter_peek (enc->multipass_cache_adapter, bytes_read);
+ cache_data = gst_adapter_map (enc->multipass_cache_adapter, bytes_read);
bytes_consumed =
th_encode_ctl (enc->encoder, TH_ENCCTL_2PASS_IN, (guint8 *) cache_data,
bytes_read);
+ gst_adapter_unmap (enc->multipass_cache_adapter, 0);
+
done = bytes_consumed <= 0;
if (bytes_consumed > 0)
gst_adapter_flush (enc->multipass_cache_adapter, bytes_consumed);
GstFlowReturn ret;
th_ycbcr_buffer ycbcr;
gint res;
+ guint8 *data;
+ gsize size;
- theora_enc_init_buffer (ycbcr, &enc->info, GST_BUFFER_DATA (buffer));
+ data = gst_buffer_map (buffer, &size, NULL, GST_MAP_READ);
+ theora_enc_init_buffer (ycbcr, &enc->info, data);
if (theora_enc_is_discontinuous (enc, running_time, duration)) {
theora_enc_reset (enc);
if (ret != GST_FLOW_OK)
goto data_push;
}
+
+done:
+ gst_buffer_unmap (buffer, data, size);
gst_buffer_unref (buffer);
return ret;
/* ERRORS */
multipass_read_failed:
{
- gst_buffer_unref (buffer);
- return ret;
+ GST_DEBUG_OBJECT (enc, "multipass read failed");
+ goto done;
}
multipass_write_failed:
{
- gst_buffer_unref (buffer);
- return ret;
+ GST_DEBUG_OBJECT (enc, "multipass write failed");
+ goto done;
}
data_push:
{
- gst_buffer_unref (buffer);
- return ret;
+ GST_DEBUG_OBJECT (enc, "error pushing buffer: %s", gst_flow_get_name (ret));
+ goto done;
}
}
caps = theora_set_header_on_caps (caps, buffers);
GST_DEBUG ("here are the caps: %" GST_PTR_FORMAT, caps);
gst_pad_set_caps (enc->srcpad, caps);
-
- g_slist_foreach (buffers, (GFunc) gst_buffer_set_caps, caps);
-
gst_caps_unref (caps);
/* push out the header buffers */
break;
}
- ret = parent_class->change_state (element, transition);
+ ret = GST_ELEMENT_CLASS (parent_class)->change_state (element, transition);
switch (transition) {
case GST_STATE_CHANGE_PLAYING_TO_PAUSED: