static void gst_sdp_demux_stream_free (GstSDPDemux * demux, GstSDPStream * stream) { gint i; GST_DEBUG_OBJECT (demux, "free stream %p", stream); if (stream->caps) gst_caps_unref (stream->caps); for (i = 0; i < 2; i++) { GstElement *udpsrc = stream->udpsrc[i]; if (udpsrc) { gst_element_set_state (udpsrc, GST_STATE_NULL); gst_bin_remove (GST_BIN_CAST (demux), udpsrc); stream->udpsrc[i] = NULL; } } if (stream->udpsink) { gst_element_set_state (stream->udpsink, GST_STATE_NULL); gst_bin_remove (GST_BIN_CAST (demux), stream->udpsink); stream->udpsink = NULL; } if (stream->srcpad) { gst_pad_set_active (stream->srcpad, FALSE); if (stream->added) { gst_element_remove_pad (GST_ELEMENT_CAST (demux), stream->srcpad); stream->added = FALSE; } stream->srcpad = NULL; } g_free (stream); }
static GstStateChangeReturn gst_play_sink_video_convert_change_state (GstElement * element, GstStateChange transition) { GstStateChangeReturn ret; GstPlaySinkVideoConvert *self = GST_PLAY_SINK_VIDEO_CONVERT_CAST (element); switch (transition) { case GST_STATE_CHANGE_PAUSED_TO_READY: GST_PLAY_SINK_VIDEO_CONVERT_LOCK (self); if (gst_pad_is_blocked (self->sink_proxypad)) gst_pad_set_blocked_async_full (self->sink_proxypad, FALSE, (GstPadBlockCallback) pad_blocked_cb, gst_object_ref (self), (GDestroyNotify) gst_object_unref); GST_PLAY_SINK_VIDEO_CONVERT_UNLOCK (self); break; default: break; } ret = GST_ELEMENT_CLASS (parent_class)->change_state (element, transition); if (ret == GST_STATE_CHANGE_FAILURE) return ret; switch (transition) { case GST_STATE_CHANGE_PAUSED_TO_READY: GST_PLAY_SINK_VIDEO_CONVERT_LOCK (self); gst_segment_init (&self->segment, GST_FORMAT_UNDEFINED); if (self->conv) { gst_element_set_state (self->conv, GST_STATE_NULL); gst_bin_remove (GST_BIN_CAST (self), self->conv); self->conv = NULL; } if (self->scale) { gst_element_set_state (self->scale, GST_STATE_NULL); gst_bin_remove (GST_BIN_CAST (self), self->scale); self->scale = NULL; } gst_ghost_pad_set_target (GST_GHOST_PAD_CAST (self->srcpad), self->sink_proxypad); self->raw = FALSE; GST_PLAY_SINK_VIDEO_CONVERT_UNLOCK (self); break; case GST_STATE_CHANGE_READY_TO_PAUSED: GST_PLAY_SINK_VIDEO_CONVERT_LOCK (self); if (!gst_pad_is_blocked (self->sink_proxypad)) gst_pad_set_blocked_async_full (self->sink_proxypad, TRUE, (GstPadBlockCallback) pad_blocked_cb, gst_object_ref (self), (GDestroyNotify) gst_object_unref); GST_PLAY_SINK_VIDEO_CONVERT_UNLOCK (self); default: break; } return ret; }
static GstBin * kms_agnostic_bin2_find_bin_for_caps (KmsAgnosticBin2 * self, GstCaps * caps) { GList *bins, *l; GstBin *bin = NULL; if (gst_caps_is_any (caps) || gst_caps_is_empty (caps)) { return self->priv->input_bin; } if (check_bin (KMS_TREE_BIN (self->priv->input_bin), caps)) { bin = self->priv->input_bin; } bins = g_hash_table_get_values (self->priv->bins); for (l = bins; l != NULL && bin == NULL; l = l->next) { KmsTreeBin *tree_bin = KMS_TREE_BIN (l->data); if (check_bin (tree_bin, caps)) { bin = GST_BIN_CAST (tree_bin); } } g_list_free (bins); return bin; }
static GObject * gst_gl_mixer_bin_child_proxy_get_child_by_index (GstChildProxy * child_proxy, guint index) { GstGLMixerBin *mixer = GST_GL_MIXER_BIN (child_proxy); GstBin *bin = GST_BIN_CAST (child_proxy); GObject *res = NULL; GST_OBJECT_LOCK (bin); /* XXX: not exactly thread safe with ordering */ if (index < bin->numchildren) { if ((res = g_list_nth_data (bin->children, index))) gst_object_ref (res); } else { struct input_chain *chain; if ((chain = g_list_nth_data (mixer->priv->input_chains, index - bin->numchildren))) { res = gst_object_ref (chain->ghost_pad); } } GST_OBJECT_UNLOCK (bin); return res; }
static void gst_sdp_demux_cleanup (GstSDPDemux * demux) { GList *walk; GST_DEBUG_OBJECT (demux, "cleanup"); for (walk = demux->streams; walk; walk = g_list_next (walk)) { GstSDPStream *stream = (GstSDPStream *) walk->data; gst_sdp_demux_stream_free (demux, stream); } g_list_free (demux->streams); demux->streams = NULL; if (demux->session) { if (demux->session_sig_id) { g_signal_handler_disconnect (demux->session, demux->session_sig_id); demux->session_sig_id = 0; } gst_element_set_state (demux->session, GST_STATE_NULL); gst_bin_remove (GST_BIN_CAST (demux), demux->session); demux->session = NULL; } demux->numstreams = 0; }
/** * ges_pipeline_add_timeline: * @pipeline: a #GESPipeline * @timeline: the #GESTimeline to set on the @pipeline. * * Sets the timeline to use in this pipeline. * * The reference to the @timeline will be stolen by the @pipeline. * * Returns: TRUE if the @timeline could be successfully set on the @pipeline, * else FALSE. */ gboolean ges_pipeline_add_timeline (GESPipeline * pipeline, GESTimeline * timeline) { g_return_val_if_fail (GES_IS_PIPELINE (pipeline), FALSE); g_return_val_if_fail (GES_IS_TIMELINE (timeline), FALSE); g_return_val_if_fail (pipeline->priv->timeline == NULL, FALSE); GST_DEBUG ("pipeline:%p, timeline:%p", timeline, pipeline); if (G_UNLIKELY (!gst_bin_add (GST_BIN_CAST (pipeline), GST_ELEMENT (timeline)))) { return FALSE; } pipeline->priv->timeline = timeline; /* Connect to pipeline */ g_signal_connect (timeline, "pad-added", (GCallback) pad_added_cb, pipeline); g_signal_connect (timeline, "pad-removed", (GCallback) pad_removed_cb, pipeline); g_signal_connect (timeline, "no-more-pads", (GCallback) no_more_pads_cb, pipeline); /* FIXME Check if we should rollback if we can't sync state */ gst_element_sync_state_with_parent (GST_ELEMENT (timeline)); return TRUE; }
static gboolean gst_wrapper_camera_bin_src_set_mode (GstBaseCameraSrc * bcamsrc, GstCameraBinMode mode) { GstPhotography *photography = (GstPhotography *) gst_bin_get_by_interface (GST_BIN_CAST (bcamsrc), GST_TYPE_PHOTOGRAPHY); GstWrapperCameraBinSrc *self = GST_WRAPPER_CAMERA_BIN_SRC (bcamsrc); if (self->output_selector) { if (mode == MODE_IMAGE) { self->image_renegotiate = TRUE; g_object_set (self->output_selector, "active-pad", self->outsel_imgpad, NULL); } else { self->video_renegotiate = TRUE; g_object_set (self->output_selector, "active-pad", self->outsel_vidpad, NULL); } } self->mode = mode; if (photography) { if (g_object_class_find_property (G_OBJECT_GET_CLASS (photography), "capture-mode")) { g_object_set (G_OBJECT (photography), "capture-mode", mode, NULL); } } else { GstCaps *anycaps = gst_caps_new_any (); gst_wrapper_camera_bin_reset_video_src_caps (self, anycaps); gst_caps_unref (anycaps); } return TRUE; }
/** * ges_pipeline_set_timeline: * @pipeline: a #GESPipeline * @timeline: the #GESTimeline to set on the @pipeline. * * Sets the timeline to use in this pipeline. * * The reference to the @timeline will be stolen by the @pipeline. * * Returns: TRUE if the @timeline could be successfully set on the @pipeline, * else FALSE. */ gboolean ges_pipeline_set_timeline (GESPipeline * pipeline, GESTimeline * timeline) { g_return_val_if_fail (GES_IS_PIPELINE (pipeline), FALSE); g_return_val_if_fail (GES_IS_TIMELINE (timeline), FALSE); g_return_val_if_fail (pipeline->priv->timeline == NULL, FALSE); GST_DEBUG ("pipeline:%p, timeline:%p", timeline, pipeline); if (G_UNLIKELY (!gst_bin_add (GST_BIN_CAST (pipeline), GST_ELEMENT (timeline)))) { return FALSE; } pipeline->priv->timeline = timeline; g_signal_connect (timeline, "track-added", G_CALLBACK (_timeline_track_added_cb), pipeline); g_signal_connect (timeline, "track-removed", G_CALLBACK (_timeline_track_removed_cb), pipeline); /* FIXME Check if we should rollback if we can't sync state */ gst_element_sync_state_with_parent (GST_ELEMENT (timeline)); return TRUE; }
static void type_found (GstElement * typefind, guint probability, GstCaps * caps, GstSplitMuxPartReader * reader) { GstElement *demux; GST_INFO_OBJECT (reader, "Got type %" GST_PTR_FORMAT, caps); /* typefind found a type. Look for the demuxer to handle it */ demux = reader->demux = find_demuxer (caps); if (reader->demux == NULL) { GST_ERROR_OBJECT (reader, "Failed to create demuxer element"); return; } /* Connect to demux signals */ g_signal_connect (demux, "pad-added", G_CALLBACK (new_decoded_pad_added_cb), reader); g_signal_connect (demux, "no-more-pads", G_CALLBACK (no_more_pads), reader); gst_element_set_locked_state (demux, TRUE); gst_bin_add (GST_BIN_CAST (reader), demux); gst_element_link_pads (reader->typefind, "src", demux, NULL); gst_element_set_state (reader->demux, GST_STATE_TARGET (reader)); gst_element_set_locked_state (demux, FALSE); }
static void gst_vt_h264_enc_bin_init (GstVTH264EncBin * self, GstVTH264EncBinClass * gclass) { GstVTH264EncBinPrivate *priv; GstPad *encoder_sinkpad, *parser_srcpad, *ghost_pad; self->priv = priv = TAA_VT_H264_ENC_BIN_GET_PRIVATE (self); priv->encoder = gst_element_factory_make ("vtenc_h264", "encoder"); priv->parser = gst_element_factory_make ("h264parse", "parser"); gst_bin_add_many (GST_BIN_CAST (self), priv->encoder, priv->parser, NULL); gst_element_link (priv->encoder, priv->parser); encoder_sinkpad = gst_element_get_static_pad (priv->encoder, "sink"); ghost_pad = gst_ghost_pad_new_from_template ("sink", encoder_sinkpad, gst_static_pad_template_get (&vth264encbin_sink_template)); gst_object_unref (encoder_sinkpad); gst_element_add_pad (GST_ELEMENT_CAST (self), ghost_pad); parser_srcpad = gst_element_get_static_pad (priv->parser, "src"); ghost_pad = gst_ghost_pad_new_from_template ("src", parser_srcpad, gst_static_pad_template_get (&vth264encbin_src_template)); gst_object_unref (parser_srcpad); gst_element_add_pad (GST_ELEMENT_CAST (self), ghost_pad); g_object_set (priv->encoder, "usage", 6, NULL); g_object_set (priv->parser, "output-format", H264PARSE_OUTPUT_FORMAT_BYTE_STREAM, "split-packetized", TRUE, NULL); }
static void gst_play_sink_convert_bin_remove_element (GstElement * element, GstPlaySinkConvertBin * self) { gst_element_set_state (element, GST_STATE_NULL); gst_object_unref (element); gst_bin_remove (GST_BIN_CAST (self), element); }
static gboolean start_image_capture (GstWrapperCameraBinSrc * self) { GstBaseCameraSrc *bcamsrc = GST_BASE_CAMERA_SRC (self); GstPhotography *photography = (GstPhotography *) gst_bin_get_by_interface (GST_BIN_CAST (bcamsrc), GST_TYPE_PHOTOGRAPHY); gboolean ret = FALSE; GstCaps *caps; GST_DEBUG_OBJECT (self, "Starting image capture"); gst_element_set_state (self->src_vid_src, GST_STATE_READY); if (self->image_renegotiate) { /* clean capsfilter caps so they don't interfere here */ g_object_set (self->src_filter, "caps", NULL, NULL); if (self->src_zoom_filter) g_object_set (self->src_zoom_filter, "caps", NULL, NULL); caps = gst_pad_get_allowed_caps (self->imgsrc); gst_caps_replace (&self->image_capture_caps, caps); gst_caps_unref (caps); /* FIXME - do we need to update basecamerasrc width/height somehow here? * if not, i think we need to do something about _when_ they get updated * to be sure that set_element_zoom doesn't use the wrong values */ /* We caught this event in the src pad event handler and now we want to * actually push it upstream */ gst_pad_send_event (self->outsel_imgpad, gst_event_new_reconfigure ()); self->image_renegotiate = FALSE; } if (photography) { gst_element_set_state (self->src_vid_src, GST_STATE_PLAYING); GST_DEBUG_OBJECT (self, "prepare image capture caps %" GST_PTR_FORMAT, self->image_capture_caps); ret = gst_photography_prepare_for_capture (photography, (GstPhotographyCapturePrepared) img_capture_prepared, self->image_capture_caps, self); } else { g_mutex_unlock (&bcamsrc->capturing_mutex); gst_wrapper_camera_bin_reset_video_src_caps (self, self->image_capture_caps); g_mutex_lock (&bcamsrc->capturing_mutex); ret = TRUE; gst_element_set_state (self->src_vid_src, GST_STATE_PLAYING); } return ret; }
static void _element_added_callback (GstBin *parent, GstElement *element, gpointer user_data) { FsElementAddedNotifier *notifier = FS_ELEMENT_ADDED_NOTIFIER (user_data); if (GST_IS_BIN (element)) { GstIterator *iter = NULL; gboolean done; g_signal_connect_object (element, "element-added", G_CALLBACK (_element_added_callback), notifier, 0); if (parent) g_signal_connect_object (element, "parent-unset", G_CALLBACK (_bin_unparented_cb), notifier, 0); iter = gst_bin_iterate_elements (GST_BIN (element)); done = FALSE; while (!done) { gpointer item = NULL; switch (gst_iterator_next (iter, &item)) { case GST_ITERATOR_OK: /* We make sure the callback has not already been added */ if (g_signal_handler_find (item, G_SIGNAL_MATCH_FUNC | G_SIGNAL_MATCH_DATA, 0, 0, NULL, /* id, detail, closure */ _element_added_callback, notifier) == 0) _element_added_callback (GST_BIN_CAST (element), item, notifier); gst_object_unref (item); break; case GST_ITERATOR_RESYNC: // We don't rollback anything, we just ignore already processed ones gst_iterator_resync (iter); break; case GST_ITERATOR_ERROR: g_error ("Wrong parameters were given?"); done = TRUE; break; case GST_ITERATOR_DONE: done = TRUE; break; } } gst_iterator_free (iter); } g_signal_emit (notifier, signals[ELEMENT_ADDED], 0, parent, element); }
static guint gst_gl_mixer_bin_child_proxy_get_children_count (GstChildProxy * child_proxy) { GstGLMixerBin *mixer = GST_GL_MIXER_BIN (child_proxy); GstBin *bin = GST_BIN_CAST (child_proxy); guint num; GST_OBJECT_LOCK (bin); num = bin->numchildren + g_list_length (mixer->priv->input_chains); GST_OBJECT_UNLOCK (bin); return num; }
static void gst_splitmux_part_reader_init (GstSplitMuxPartReader * reader) { GstElement *typefind; reader->active = FALSE; reader->duration = GST_CLOCK_TIME_NONE; g_cond_init (&reader->inactive_cond); g_mutex_init (&reader->lock); g_mutex_init (&reader->type_lock); /* FIXME: Create elements on a state change */ reader->src = gst_element_factory_make ("filesrc", NULL); if (reader->src == NULL) { GST_ERROR_OBJECT (reader, "Failed to create filesrc element"); return; } gst_bin_add (GST_BIN_CAST (reader), reader->src); typefind = gst_element_factory_make ("typefind", NULL); if (!typefind) { GST_ERROR_OBJECT (reader, "Failed to create typefind element - check your installation"); return; } gst_bin_add (GST_BIN_CAST (reader), typefind); reader->typefind = typefind; if (!gst_element_link_pads (reader->src, NULL, typefind, "sink")) { GST_ERROR_OBJECT (reader, "Failed to link typefind element - check your installation"); return; } g_signal_connect (reader->typefind, "have-type", G_CALLBACK (type_found), reader); }
/** * gst_pipeline_set_latency: * @pipeline: a [GstPipeline]() * @latency: latency to configure * * Sets the latency that should be configured on the pipeline. Setting * GST_CLOCK_TIME_NONE will restore the default behaviour of using the minimum * latency from the LATENCY query. Setting this is usually not required and * the pipeline will figure out an appropriate latency automatically. * * Setting a too low latency, especially lower than the minimum latency from * the LATENCY query, will most likely cause the pipeline to fail. * * Since: 1.6 */ void gst_pipeline_set_latency (GstPipeline * pipeline, GstClockTime latency) { gboolean changed; g_return_if_fail (GST_IS_PIPELINE (pipeline)); GST_OBJECT_LOCK (pipeline); changed = (pipeline->priv->latency != latency); pipeline->priv->latency = latency; GST_OBJECT_UNLOCK (pipeline); if (changed) gst_bin_recalculate_latency (GST_BIN_CAST (pipeline)); }
static void gst_rg_volume_dispose (GObject * object) { GstRgVolume *self = GST_RG_VOLUME (object); if (self->volume_element != NULL) { /* Manually remove our child using the bin implementation of remove_element. * This is needed because we prevent gst_bin_remove from working, which the * parent dispose handler would use if we had any children left. */ GST_BIN_CLASS (parent_class)->remove_element (GST_BIN_CAST (self), self->volume_element); self->volume_element = NULL; } G_OBJECT_CLASS (parent_class)->dispose (object); }
static void gst_rg_volume_init (GstRgVolume * self) { GObjectClass *volume_class; GstPad *volume_pad, *ghost_pad; self->album_mode = DEFAULT_ALBUM_MODE; self->headroom = DEFAULT_HEADROOM; self->pre_amp = DEFAULT_PRE_AMP; self->fallback_gain = DEFAULT_FALLBACK_GAIN; self->target_gain = 0.0; self->result_gain = 0.0; self->volume_element = gst_element_factory_make ("volume", "rgvolume-volume"); if (G_UNLIKELY (self->volume_element == NULL)) { GstMessage *msg; GST_WARNING_OBJECT (self, "could not create volume element"); msg = gst_missing_element_message_new (GST_ELEMENT_CAST (self), "volume"); gst_element_post_message (GST_ELEMENT_CAST (self), msg); /* Nothing else to do, we will refuse the state change from NULL to READY to * indicate that something went very wrong. It is doubtful that someone * attempts changing our state though, since we end up having no pads! */ return; } volume_class = G_OBJECT_GET_CLASS (G_OBJECT (self->volume_element)); self->max_volume = G_PARAM_SPEC_DOUBLE (g_object_class_find_property (volume_class, "volume"))->maximum; GST_BIN_CLASS (parent_class)->add_element (GST_BIN_CAST (self), self->volume_element); volume_pad = gst_element_get_static_pad (self->volume_element, "sink"); ghost_pad = gst_ghost_pad_new_from_template ("sink", volume_pad, gst_pad_get_pad_template (volume_pad)); gst_object_unref (volume_pad); gst_pad_set_event_function (ghost_pad, gst_rg_volume_sink_event); gst_element_add_pad (GST_ELEMENT_CAST (self), ghost_pad); volume_pad = gst_element_get_static_pad (self->volume_element, "src"); ghost_pad = gst_ghost_pad_new_from_template ("src", volume_pad, gst_pad_get_pad_template (volume_pad)); gst_object_unref (volume_pad); gst_element_add_pad (GST_ELEMENT_CAST (self), ghost_pad); }
/* start a bin with the given description */ static GstElement * create_stream (const gchar * descr) { GstElement *bin; GError *error = NULL; bin = gst_parse_launch (descr, &error); if (error) { g_print ("pipeline could not be constructed: %s\n", error->message); g_error_free (error); return NULL; } /* add the bin to the pipeline now, this will set the current base_time of the * pipeline on the new bin. */ gst_bin_add (GST_BIN_CAST (pipeline), bin); return bin; }
static gboolean start_image_capture (GstWrapperCameraBinSrc * self) { GstBaseCameraSrc *bcamsrc = GST_BASE_CAMERA_SRC (self); GstPhotography *photography = (GstPhotography *) gst_bin_get_by_interface (GST_BIN_CAST (bcamsrc), GST_TYPE_PHOTOGRAPHY); gboolean ret = FALSE; GstCaps *caps; GST_DEBUG_OBJECT (self, "Starting image capture"); if (self->image_renegotiate) { /* clean capsfilter caps so they don't interfere here */ g_object_set (self->src_filter, "caps", NULL, NULL); if (self->src_zoom_filter) g_object_set (self->src_zoom_filter, "caps", NULL, NULL); caps = gst_pad_get_allowed_caps (self->imgsrc); gst_caps_replace (&self->image_capture_caps, caps); gst_caps_unref (caps); self->image_renegotiate = FALSE; } if (photography) { GST_DEBUG_OBJECT (self, "prepare image capture caps %" GST_PTR_FORMAT, self->image_capture_caps); ret = gst_photography_prepare_for_capture (photography, (GstPhotoCapturePrepared) img_capture_prepared, self->image_capture_caps, self); } else { g_mutex_unlock (bcamsrc->capturing_mutex); gst_wrapper_camera_bin_reset_video_src_caps (self, self->image_capture_caps); g_mutex_lock (bcamsrc->capturing_mutex); ret = TRUE; } return ret; }
static GstElement * default_create_pipeline (GstRTSPMediaFactory * factory, GstRTSPMedia * media) { GstElement *pipeline; if (media->element == NULL) goto no_element; pipeline = gst_pipeline_new ("media-pipeline"); gst_bin_add (GST_BIN_CAST (pipeline), media->element); return pipeline; /* ERRORS */ no_element: { g_critical ("no element"); return NULL; } }
void gst_play_sink_convert_bin_add_identity (GstPlaySinkConvertBin * self) { if (self->identity) return; self->identity = gst_element_factory_make ("identity", "identity"); if (self->identity == NULL) { gst_play_sink_convert_bin_post_missing_element_message (self, "identity"); GST_ELEMENT_WARNING (self, CORE, MISSING_PLUGIN, (_("Missing element '%s' - check your GStreamer installation."), "identity"), (self->audio ? "audio rendering might fail" : "video rendering might fail") ); } else { g_object_set (self->identity, "silent", TRUE, "signal-handoffs", FALSE, NULL); gst_bin_add (GST_BIN_CAST (self), self->identity); } }
void totem_gst_message_print (GstMessage *msg, GstElement *play, const char *filename) { GError *err = NULL; char *dbg = NULL; g_return_if_fail (GST_MESSAGE_TYPE (msg) == GST_MESSAGE_ERROR); if (play != NULL) { g_return_if_fail (filename != NULL); GST_DEBUG_BIN_TO_DOT_FILE (GST_BIN_CAST (play), GST_DEBUG_GRAPH_SHOW_ALL ^ GST_DEBUG_GRAPH_SHOW_NON_DEFAULT_PARAMS, filename); } gst_message_parse_error (msg, &err, &dbg); if (err) { char *uri; g_object_get (play, "uri", &uri, NULL); GST_ERROR ("message = %s", GST_STR_NULL (err->message)); GST_ERROR ("domain = %d (%s)", err->domain, GST_STR_NULL (g_quark_to_string (err->domain))); GST_ERROR ("code = %d", err->code); GST_ERROR ("debug = %s", GST_STR_NULL (dbg)); GST_ERROR ("source = %" GST_PTR_FORMAT, msg->src); GST_ERROR ("uri = %s", GST_STR_NULL (uri)); g_free (uri); g_message ("Error: %s\n%s\n", GST_STR_NULL (err->message), GST_STR_NULL (dbg)); g_error_free (err); } g_free (dbg); }
/** * ges_timeline_pipeline_add_timeline: * @pipeline: a #GESTimelinePipeline * @timeline: the #GESTimeline to set on the @pipeline. * * Sets the timeline to use in this pipeline. * * The reference to the @timeline will be stolen by the @pipeline. * * Returns: TRUE if the @timeline could be successfully set on the @pipeline, * else FALSE. */ gboolean ges_timeline_pipeline_add_timeline (GESTimelinePipeline * pipeline, GESTimeline * timeline) { g_return_val_if_fail (pipeline->priv->timeline == NULL, FALSE); g_return_val_if_fail (timeline != NULL, FALSE); GST_DEBUG ("pipeline:%p, timeline:%p", timeline, pipeline); if (G_UNLIKELY (!gst_bin_add (GST_BIN_CAST (pipeline), GST_ELEMENT (timeline)))) { return FALSE; } pipeline->priv->timeline = timeline; /* Connect to pipeline */ g_signal_connect (timeline, "pad-added", (GCallback) pad_added_cb, pipeline); g_signal_connect (timeline, "pad-removed", (GCallback) pad_removed_cb, pipeline); return TRUE; }
/** * gst_validate_monitor_factory_create: * @target: The #GstObject to create a #GstValidateMonitor for * @runner: The #GstValidateRunner to use for the new monitor * @parent: (nullable): The parent of the new monitor * * Create a new monitor for @target and starts monitoring it. * * Returns: (transfer full): The newly created #GstValidateMonitor */ GstValidateMonitor * gst_validate_monitor_factory_create (GstObject * target, GstValidateRunner * runner, GstValidateMonitor * parent) { GstValidateMonitor *monitor = NULL; g_return_val_if_fail (target != NULL, NULL); monitor = g_object_get_data ((GObject *) target, "validate-monitor"); if (monitor) { GST_INFO_OBJECT (target, "Is already monitored by %" GST_PTR_FORMAT, monitor); return g_object_ref (monitor); } if (GST_IS_PAD (target)) { monitor = GST_VALIDATE_MONITOR_CAST (gst_validate_pad_monitor_new (GST_PAD_CAST (target), runner, GST_VALIDATE_ELEMENT_MONITOR_CAST (parent))); } else if (GST_IS_PIPELINE (target)) { monitor = GST_VALIDATE_MONITOR_CAST (gst_validate_pipeline_monitor_new (GST_PIPELINE_CAST (target), runner, parent)); } else if (GST_IS_BIN (target)) { monitor = GST_VALIDATE_MONITOR_CAST (gst_validate_bin_monitor_new (GST_BIN_CAST (target), runner, parent)); } else if (GST_IS_ELEMENT (target)) { monitor = GST_VALIDATE_MONITOR_CAST (gst_validate_element_monitor_new (GST_ELEMENT_CAST (target), runner, parent)); } else { g_assert_not_reached (); } return monitor; }
static gboolean gst_hls_sink_create_elements (GstHlsSink * sink) { GstPad *pad = NULL; GST_DEBUG_OBJECT (sink, "Creating internal elements"); if (sink->elements_created) return TRUE; sink->multifilesink = gst_element_factory_make ("multifilesink", NULL); if (sink->multifilesink == NULL) goto missing_element; g_object_set (sink->multifilesink, "location", sink->location, "next-file", 3, "post-messages", TRUE, "max-files", sink->max_files, NULL); gst_bin_add (GST_BIN_CAST (sink), sink->multifilesink); pad = gst_element_get_static_pad (sink->multifilesink, "sink"); gst_ghost_pad_set_target (GST_GHOST_PAD (sink->ghostpad), pad); gst_object_unref (pad); sink->elements_created = TRUE; return TRUE; missing_element: gst_element_post_message (GST_ELEMENT_CAST (sink), gst_missing_element_message_new (GST_ELEMENT_CAST (sink), "multifilesink")); GST_ELEMENT_ERROR (sink, CORE, MISSING_PLUGIN, (("Missing element '%s' - check your GStreamer installation."), "multifilesink"), (NULL)); return FALSE; }
static void pad_blocked_cb (GstPad * pad, gboolean blocked, GstPlaySinkVideoConvert * self) { GstPad *peer; GstCaps *caps; gboolean raw; GST_PLAY_SINK_VIDEO_CONVERT_LOCK (self); self->sink_proxypad_blocked = blocked; GST_DEBUG_OBJECT (self, "Pad blocked: %d", blocked); if (!blocked) goto done; /* There must be a peer at this point */ peer = gst_pad_get_peer (self->sinkpad); caps = gst_pad_get_negotiated_caps (peer); if (!caps) caps = gst_pad_get_caps_reffed (peer); gst_object_unref (peer); raw = is_raw_caps (caps); GST_DEBUG_OBJECT (self, "Caps %" GST_PTR_FORMAT " are raw: %d", caps, raw); gst_caps_unref (caps); if (raw == self->raw) goto unblock; self->raw = raw; if (raw) { GstBin *bin = GST_BIN_CAST (self); GstElement *head = NULL, *prev = NULL; GstPad *pad; GST_DEBUG_OBJECT (self, "Creating raw conversion pipeline"); gst_ghost_pad_set_target (GST_GHOST_PAD_CAST (self->sinkpad), NULL); gst_ghost_pad_set_target (GST_GHOST_PAD_CAST (self->srcpad), NULL); self->conv = gst_element_factory_make ("ffmpegcolorspace", "conv"); if (self->conv == NULL) { post_missing_element_message (self, "ffmpegcolorspace"); GST_ELEMENT_WARNING (self, CORE, MISSING_PLUGIN, (_("Missing element '%s' - check your GStreamer installation."), "ffmpegcolorspace"), ("video rendering might fail")); } else { gst_bin_add (bin, self->conv); gst_element_sync_state_with_parent (self->conv); distribute_running_time (self->conv, &self->segment); prev = head = self->conv; } self->scale = gst_element_factory_make ("videoscale", "scale"); if (self->scale == NULL) { post_missing_element_message (self, "videoscale"); GST_ELEMENT_WARNING (self, CORE, MISSING_PLUGIN, (_("Missing element '%s' - check your GStreamer installation."), "videoscale"), ("possibly a liboil version mismatch?")); } else { /* Add black borders if necessary to keep the DAR */ g_object_set (self->scale, "add-borders", TRUE, NULL); gst_bin_add (bin, self->scale); gst_element_sync_state_with_parent (self->scale); distribute_running_time (self->scale, &self->segment); if (prev) { if (!gst_element_link_pads_full (prev, "src", self->scale, "sink", GST_PAD_LINK_CHECK_TEMPLATE_CAPS)) goto link_failed; } else { head = self->scale; } prev = self->scale; } if (head) { pad = gst_element_get_static_pad (head, "sink"); gst_ghost_pad_set_target (GST_GHOST_PAD_CAST (self->sinkpad), pad); gst_object_unref (pad); } if (prev) { pad = gst_element_get_static_pad (prev, "src"); gst_ghost_pad_set_target (GST_GHOST_PAD_CAST (self->srcpad), pad); gst_object_unref (pad); } if (!head && !prev) { gst_ghost_pad_set_target (GST_GHOST_PAD_CAST (self->srcpad), self->sink_proxypad); } GST_DEBUG_OBJECT (self, "Raw conversion pipeline created"); } else { GstBin *bin = GST_BIN_CAST (self); GST_DEBUG_OBJECT (self, "Removing raw conversion pipeline"); gst_ghost_pad_set_target (GST_GHOST_PAD_CAST (self->sinkpad), NULL); gst_ghost_pad_set_target (GST_GHOST_PAD_CAST (self->srcpad), NULL); if (self->conv) { gst_element_set_state (self->conv, GST_STATE_NULL); gst_bin_remove (bin, self->conv); self->conv = NULL; } if (self->scale) { gst_element_set_state (self->scale, GST_STATE_NULL); gst_bin_remove (bin, self->scale); self->scale = NULL; } gst_ghost_pad_set_target (GST_GHOST_PAD_CAST (self->srcpad), self->sink_proxypad); GST_DEBUG_OBJECT (self, "Raw conversion pipeline removed"); } unblock: gst_pad_set_blocked_async_full (self->sink_proxypad, FALSE, (GstPadBlockCallback) pad_blocked_cb, gst_object_ref (self), (GDestroyNotify) gst_object_unref); done: GST_PLAY_SINK_VIDEO_CONVERT_UNLOCK (self); return; link_failed: { GST_ELEMENT_ERROR (self, CORE, PAD, (NULL), ("Failed to configure the video converter.")); gst_ghost_pad_set_target (GST_GHOST_PAD_CAST (self->srcpad), self->sink_proxypad); gst_pad_set_blocked_async_full (self->sink_proxypad, FALSE, (GstPadBlockCallback) pad_blocked_cb, gst_object_ref (self), (GDestroyNotify) gst_object_unref); return; } }
static void test_element2_init (TestElement2 * elem) { configure_test_element (GST_BIN_CAST (elem), "test/caps,type=(int)2"); }
/** * check_and_replace_src * @self: #GstWrapperCamerabinSrcCameraSrc object * * Checks if the current videosrc needs to be replaced */ static gboolean check_and_replace_src (GstWrapperCameraBinSrc * self) { GstBin *cbin = GST_BIN_CAST (self); GstBaseCameraSrc *bcamsrc = GST_BASE_CAMERA_SRC_CAST (self); if (self->src_vid_src && self->src_vid_src == self->app_vid_src) { GST_DEBUG_OBJECT (self, "No need to change current videosrc"); return TRUE; } if (self->src_vid_src) { GST_DEBUG_OBJECT (self, "Removing old video source"); if (self->src_max_zoom_signal_id) { g_signal_handler_disconnect (self->src_vid_src, self->src_max_zoom_signal_id); self->src_max_zoom_signal_id = 0; } if (self->src_event_probe_id) { GstPad *pad; pad = gst_element_get_static_pad (self->src_vid_src, "src"); gst_pad_remove_probe (pad, self->src_event_probe_id); gst_object_unref (pad); self->src_event_probe_id = 0; } gst_bin_remove (GST_BIN_CAST (self), self->src_vid_src); self->src_vid_src = NULL; } GST_DEBUG_OBJECT (self, "Adding new video source"); /* Add application set or default video src element */ if (!(self->src_vid_src = gst_camerabin_setup_default_element (cbin, self->app_vid_src, "autovideosrc", DEFAULT_VIDEOSRC, "camerasrc-real-src"))) { self->src_vid_src = NULL; return FALSE; } else { GstElement *videoconvert; if (!gst_bin_add (cbin, self->src_vid_src)) { return FALSE; } /* check if we already have the next element to link to */ videoconvert = gst_bin_get_by_name (cbin, "src-videoconvert"); if (videoconvert) { if (!gst_element_link_pads (self->src_vid_src, "src", videoconvert, "sink")) { return FALSE; } } } /* we listen for changes to max-zoom in the video src so that * we can proxy them to the basecamerasrc property */ if (g_object_class_find_property (G_OBJECT_GET_CLASS (bcamsrc), "max-zoom")) { self->src_max_zoom_signal_id = g_signal_connect (G_OBJECT (self->src_vid_src), "notify::max-zoom", (GCallback) gst_wrapper_camera_bin_src_max_zoom_cb, bcamsrc); } /* add a buffer probe to the src elemento to drop EOS from READY->NULL */ { GstPad *pad; pad = gst_element_get_static_pad (self->src_vid_src, "src"); self->src_event_probe_id = gst_pad_add_probe (pad, GST_PAD_PROBE_TYPE_EVENT_DOWNSTREAM, gst_wrapper_camera_src_src_event_probe, gst_object_ref (self), gst_object_unref); gst_object_unref (pad); } return TRUE; }
/** * ges_timeline_pipeline_set_mode: * @pipeline: a #GESTimelinePipeline * @mode: the #GESPipelineFlags to use * * switches the @pipeline to the specified @mode. The default mode when * creating a #GESTimelinePipeline is #TIMELINE_MODE_PREVIEW. * * Note: The @pipeline will be set to #GST_STATE_NULL during this call due to * the internal changes that happen. The caller will therefore have to * set the @pipeline to the requested state after calling this method. * * Returns: %TRUE if the mode was properly set, else %FALSE. **/ gboolean ges_timeline_pipeline_set_mode (GESTimelinePipeline * pipeline, GESPipelineFlags mode) { GST_DEBUG_OBJECT (pipeline, "current mode : %d, mode : %d", pipeline->priv->mode, mode); /* fast-path, nothing to change */ if (mode == pipeline->priv->mode) return TRUE; /* FIXME: It would be nice if we are only (de)activating preview * modes to not set the whole pipeline to NULL, but instead just * do the proper (un)linking to playsink. */ /* Switch pipeline to NULL since we're changing the configuration */ gst_element_set_state (GST_ELEMENT_CAST (pipeline), GST_STATE_NULL); /* remove no-longer needed components */ if (pipeline->priv->mode & TIMELINE_MODE_PREVIEW && !(mode & TIMELINE_MODE_PREVIEW)) { /* Disable playsink */ GST_DEBUG ("Disabling playsink"); g_object_ref (pipeline->priv->playsink); gst_bin_remove (GST_BIN_CAST (pipeline), pipeline->priv->playsink); } if ((pipeline->priv->mode & (TIMELINE_MODE_RENDER | TIMELINE_MODE_SMART_RENDER)) && !(mode & (TIMELINE_MODE_RENDER | TIMELINE_MODE_SMART_RENDER))) { /* Disable render bin */ GST_DEBUG ("Disabling rendering bin"); g_object_ref (pipeline->priv->encodebin); g_object_ref (pipeline->priv->urisink); gst_bin_remove_many (GST_BIN_CAST (pipeline), pipeline->priv->encodebin, pipeline->priv->urisink, NULL); } /* Add new elements */ if (!(pipeline->priv->mode & TIMELINE_MODE_PREVIEW) && (mode & TIMELINE_MODE_PREVIEW)) { /* Add playsink */ GST_DEBUG ("Adding playsink"); if (!gst_bin_add (GST_BIN_CAST (pipeline), pipeline->priv->playsink)) { GST_ERROR_OBJECT (pipeline, "Couldn't add playsink"); return FALSE; } } if (!(pipeline->priv->mode & (TIMELINE_MODE_RENDER | TIMELINE_MODE_SMART_RENDER)) && (mode & (TIMELINE_MODE_RENDER | TIMELINE_MODE_SMART_RENDER))) { /* Adding render bin */ GST_DEBUG ("Adding render bin"); if (G_UNLIKELY (pipeline->priv->urisink == NULL)) { GST_ERROR_OBJECT (pipeline, "Output URI not set !"); return FALSE; } if (!gst_bin_add (GST_BIN_CAST (pipeline), pipeline->priv->encodebin)) { GST_ERROR_OBJECT (pipeline, "Couldn't add encodebin"); return FALSE; } if (!gst_bin_add (GST_BIN_CAST (pipeline), pipeline->priv->urisink)) { GST_ERROR_OBJECT (pipeline, "Couldn't add URI sink"); return FALSE; } g_object_set (pipeline->priv->encodebin, "avoid-reencoding", !(!(mode & TIMELINE_MODE_SMART_RENDER)), NULL); gst_element_link_pads_full (pipeline->priv->encodebin, "src", pipeline->priv->urisink, "sink", GST_PAD_LINK_CHECK_NOTHING); } /* FIXUPS */ /* FIXME * If we are rendering, set playsink to sync=False, * If we are NOT rendering, set playsink to sync=TRUE */ pipeline->priv->mode = mode; return TRUE; }