/* GStreamer
 * Copyright (C) <2007> Wim Taymans <wim.taymans@gmail.com>
 * Copyright (C) <2011> Sebastian Dröge <sebastian.droege@collabora.co.uk>
 * Copyright (C) <2013> Collabora Ltd.
 *   Author: Sebastian Dröge <sebastian.droege@collabora.co.uk>
 * Copyright (C) <2015> Jan Schmidt <jan@centricular.com>
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Library General Public
 * License as published by the Free Software Foundation; either
 * version 2 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Library General Public License for more details.
 *
 * You should have received a copy of the GNU Library General Public
 * License along with this library; if not, write to the
 * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
 * Boston, MA 02110-1301, USA.
 */
/**
 * SECTION:element-playbin3
 * @title: playbin3
 *
 * playbin3 provides a stand-alone everything-in-one abstraction for an
 * audio and/or video player. It differs from the previous playbin (playbin2)
 * by supporting publication and selection of available streams via the
 * #GstStreamCollection message and #GST_EVENT_SELECT_STREAMS event API.
 *
 * <emphasis>playbin3 is still experimental API and a technology preview.
 * Its behaviour and exposed API is subject to change.</emphasis>
 *
 * playbin3 can handle both audio and video files and features
 *
 * * automatic file type recognition and based on that automatic
 * selection and usage of the right audio/video/subtitle demuxers/decoders
 *
 * * auxilliary files - such as external subtitles and audio tracks
 * * visualisations for audio files
 * * subtitle support for video files. Subtitles can be store in external
 *   files.
 * * stream selection between different video/audio/subtitles streams
 * * meta info (tag) extraction
 * * easy access to the last video sample
 * * buffering when playing streams over a network
 * * volume control with mute option
 *
 * ## Usage
 *
 * A playbin element can be created just like any other element using
 * gst_element_factory_make(). The file/URI to play should be set via the #GstPlayBin3:uri
 * property. This must be an absolute URI, relative file paths are not allowed.
 * Example URIs are file:///home/joe/movie.avi or http://www.joedoe.com/foo.ogg
 *
 * Playbin3 is a #GstPipeline. It will notify the application of everything
 * that's happening (errors, end of stream, tags found, state changes, etc.)
 * by posting messages on its #GstBus. The application needs to watch the
 * bus.
 *
 * Playback can be initiated by setting the element to PLAYING state using
 * gst_element_set_state(). Note that the state change will take place in
 * the background in a separate thread, when the function returns playback
 * is probably not happening yet and any errors might not have occured yet.
 * Applications using playbin3 should ideally be written to deal with things
 * completely asynchroneous.
 *
 * When playback has finished (an EOS message has been received on the bus)
 * or an error has occured (an ERROR message has been received on the bus) or
 * the user wants to play a different track, playbin3 should be set back to
 * READY or NULL state, then the #GstPlayBin3:uri property should be set to the
 * new location and then playbin3 be set to PLAYING state again.
 *
 * Seeking can be done using gst_element_seek_simple() or gst_element_seek()
 * on the playbin3 element. Again, the seek will not be executed
 * instantaneously, but will be done in a background thread. When the seek
 * call returns the seek will most likely still be in process. An application
 * may wait for the seek to finish (or fail) using gst_element_get_state() with
 * -1 as the timeout, but this will block the user interface and is not
 * recommended at all.
 *
 * Applications may query the current position and duration of the stream
 * via gst_element_query_position() and gst_element_query_duration() and
 * setting the format passed to GST_FORMAT_TIME. If the query was successful,
 * the duration or position will have been returned in units of nanoseconds.
 *
 * ## Advanced Usage: specifying the audio and video sink
 *
 * By default, if no audio sink or video sink has been specified via the
 * #GstPlayBin3:audio-sink or #GstPlayBin3:video-sink property, playbin3 will use the autoaudiosink
 * and autovideosink elements to find the first-best available output method.
 * This should work in most cases, but is not always desirable. Often either
 * the user or application might want to specify more explicitly what to use
 * for audio and video output.
 *
 * If the application wants more control over how audio or video should be
 * output, it may create the audio/video sink elements itself (for example
 * using gst_element_factory_make()) and provide them to playbin3 using the
 * #GstPlayBin3:audio-sink or #GstPlayBin3:video-sink property.
 *
 * GNOME-based applications, for example, will usually want to create
 * gconfaudiosink and gconfvideosink elements and make playbin3 use those,
 * so that output happens to whatever the user has configured in the GNOME
 * Multimedia System Selector configuration dialog.
 *
 * The sink elements do not necessarily need to be ready-made sinks. It is
 * possible to create container elements that look like a sink to playbin3,
 * but in reality contain a number of custom elements linked together. This
 * can be achieved by creating a #GstBin and putting elements in there and
 * linking them, and then creating a sink #GstGhostPad for the bin and pointing
 * it to the sink pad of the first element within the bin. This can be used
 * for a number of purposes, for example to force output to a particular
 * format or to modify or observe the data before it is output.
 *
 * It is also possible to 'suppress' audio and/or video output by using
 * 'fakesink' elements (or capture it from there using the fakesink element's
 * "handoff" signal, which, nota bene, is fired from the streaming thread!).
 *
 * ## Retrieving Tags and Other Meta Data
 *
 * Most of the common meta data (artist, title, etc.) can be retrieved by
 * watching for TAG messages on the pipeline's bus (see above).
 *
 * Other more specific meta information like width/height/framerate of video
 * streams or samplerate/number of channels of audio streams can be obtained
 * from the negotiated caps on the sink pads of the sinks.
 *
 * ## Buffering
 * Playbin3 handles buffering automatically for the most part, but applications
 * need to handle parts of the buffering process as well. Whenever playbin3 is
 * buffering, it will post BUFFERING messages on the bus with a percentage
 * value that shows the progress of the buffering process. Applications need
 * to set playbin3 to PLAYING or PAUSED state in response to these messages.
 * They may also want to convey the buffering progress to the user in some
 * way. Here is how to extract the percentage information from the message:
 * |[
 * switch (GST_MESSAGE_TYPE (msg)) {
 *   case GST_MESSAGE_BUFFERING: {
 *     gint percent = 0;
 *     gst_message_parse_buffering (msg, &percent);
 *     g_print ("Buffering (%u percent done)", percent);
 *     break;
 *   }
 *   ...
 * }
 * ]|
 *
 * Note that applications should keep/set the pipeline in the PAUSED state when
 * a BUFFERING message is received with a buffer percent value < 100 and set
 * the pipeline back to PLAYING state when a BUFFERING message with a value
 * of 100 percent is received (if PLAYING is the desired state, that is).
 *
 * ## Embedding the video window in your application
 * By default, playbin3 (or rather the video sinks used) will create their own
 * window. Applications will usually want to force output to a window of their
 * own, however. This can be done using the #GstVideoOverlay interface, which most
 * video sinks implement. See the documentation there for more details.
 *
 * ## Specifying which CD/DVD device to use
 *
 * The device to use for CDs/DVDs needs to be set on the source element playbin3
 * creates before it is opened. The most generic way of doing this is to connect
 * to playbin3's "source-setup" signal, which will be emitted by playbin3 when
 * it has created the source element for a particular URI. In the signal
 * callback you can check if the source element has a "device" property and set
 * it appropriately. In some cases the device can also be set as part of the
 * URI, but it depends on the elements involved if this will work or not. For
 * example, for DVD menu playback, the following syntax might work (if the
 * resindvd plugin is used): dvd://[/path/to/device]
 *
 * ## Handling redirects
 *
 * Some elements may post 'redirect' messages on the bus to tell the
 * application to open another location. These are element messages containing
 * a structure named 'redirect' along with a 'new-location' field of string
 * type. The new location may be a relative or an absolute URI. Examples
 * for such redirects can be found in many quicktime movie trailers.
 *
 * ## Examples
 * |[
 * gst-launch-1.0 -v playbin3 uri=file:///path/to/somefile.mp4
 * ]|
 *  This will play back the given AVI video file, given that the video and
 * audio decoders required to decode the content are installed. Since no
 * special audio sink or video sink is supplied (via playbin3's audio-sink or
 * video-sink properties) playbin3 will try to find a suitable audio and
 * video sink automatically using the autoaudiosink and autovideosink elements.
 * |[
 * gst-launch-1.0 -v playbin3 uri=cdda://4
 * ]|
 *  This will play back track 4 on an audio CD in your disc drive (assuming
 * the drive is detected automatically by the plugin).
 * |[
 * gst-launch-1.0 -v playbin3 uri=dvd://
 * ]|
 *  This will play back the DVD in your disc drive (assuming
 * the drive is detected automatically by the plugin).
 *
 */

#ifdef HAVE_CONFIG_H
#include "config.h"
#endif

#include <string.h>
#include <gst/gst.h>

#include <gst/gst-i18n-plugin.h>
#include <gst/pbutils/pbutils.h>
#include <gst/audio/streamvolume.h>
#include <gst/video/video-info.h>
#include <gst/video/video-multiview.h>
#include <gst/video/videooverlay.h>
#include <gst/video/navigation.h>
#include <gst/video/colorbalance.h>
#include "gstplay-enum.h"
#include "gstplayback.h"
#include "gstplaysink.h"
#include "gstsubtitleoverlay.h"
#include "gstplaybackutils.h"

GST_DEBUG_CATEGORY_STATIC (gst_play_bin3_debug);
#define GST_CAT_DEFAULT gst_play_bin3_debug

#define GST_TYPE_PLAY_BIN               (gst_play_bin3_get_type())
#define GST_PLAY_BIN3(obj)               (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_PLAY_BIN,GstPlayBin3))
#define GST_PLAY_BIN3_CLASS(klass)       (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_PLAY_BIN,GstPlayBin3Class))
#define GST_IS_PLAY_BIN(obj)            (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_PLAY_BIN))
#define GST_IS_PLAY_BIN_CLASS(klass)    (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_PLAY_BIN))

#define ULONG_TO_POINTER(number)        ((gpointer) (guintptr) (number))
#define POINTER_TO_ULONG(number)        ((guintptr) (number))

#define VOLUME_MAX_DOUBLE 10.0

typedef struct _GstPlayBin3 GstPlayBin3;
typedef struct _GstPlayBin3Class GstPlayBin3Class;
typedef struct _GstSourceGroup GstSourceGroup;
typedef struct _GstSourceCombine GstSourceCombine;
typedef struct _SourcePad SourcePad;

typedef GstCaps *(*SourceCombineGetMediaCapsFunc) (void);

/* GstSourceCombine controls all the information regarding a certain
 * media type.
 *
 * It can control a custom combiner element (by default none)
 */
struct _GstSourceCombine
{
  const gchar *media_type;      /* the media type for the combiner */
  SourceCombineGetMediaCapsFunc get_media_caps; /* more complex caps for the combiner */
  GstPlaySinkType type;         /* the sink pad type of the combiner */
  GstStreamType stream_type;    /* The GstStreamType of the combiner */

  GstElement *combiner;         /* the combiner */
  GPtrArray *channels;          /* Array of GstPad ? */

  GstPad *srcpad;               /* the source pad of the combiner */
  GstPad *sinkpad;              /* the sinkpad of the sink when the combiner
                                 * is linked */

  GPtrArray *streams;           /* Sorted array of GstStream for the given type */

  gboolean has_active_pad;      /* stream combiner has the "active-pad" property */

  gboolean is_concat;           /* The stream combiner is the 'concat' element */
};

#define GST_SOURCE_GROUP_GET_LOCK(group) (&((GstSourceGroup*)(group))->lock)
#define GST_SOURCE_GROUP_LOCK(group) (g_mutex_lock (GST_SOURCE_GROUP_GET_LOCK(group)))
#define GST_SOURCE_GROUP_UNLOCK(group) (g_mutex_unlock (GST_SOURCE_GROUP_GET_LOCK(group)))

enum
{
  PLAYBIN_STREAM_AUDIO = 0,
  PLAYBIN_STREAM_VIDEO,
  PLAYBIN_STREAM_TEXT,
  PLAYBIN_STREAM_LAST
};

/* names matching the enum above */
static const gchar *stream_type_names[] = {
  "audio", "video", "text"
};


#define STREAM_TYPES_FORMAT "s%s%s"
#define STREAM_TYPES_ARGS(s) (s) & GST_STREAM_TYPE_AUDIO ? "audio " : "", \
    (s) & GST_STREAM_TYPE_VIDEO ? "video " : "",			\
    (s) & GST_STREAM_TYPE_TEXT ? "text " : ""



#if 0                           /* AUTOPLUG DISABLED */
static void avelements_free (gpointer data);
static GSequence *avelements_create (GstPlayBin3 * playbin,
    gboolean isaudioelement);
#endif

/* The GstAudioVideoElement structure holding the audio/video decoder
 * and the audio/video sink factories together with field indicating
 * the number of common caps features */
typedef struct
{
  GstElementFactory *dec;       /* audio:video decoder */
  GstElementFactory *sink;      /* audio:video sink */
  guint n_comm_cf;              /* number of common caps features */
} GstAVElement;

/* a structure to hold information about a uridecodebin pad */
struct _SourcePad
{
  GstPad *pad;                  /* The controlled pad */
  GstStreamType stream_type;    /* stream type of the controlled pad */
  gulong event_probe_id;
};

/* a structure to hold the objects for decoding a uri and the subtitle uri
 */
struct _GstSourceGroup
{
  GstPlayBin3 *playbin;

  GMutex lock;

  gboolean valid;               /* the group has valid info to start playback */
  gboolean active;              /* the group is active */

  gboolean playing;             /* the group is currently playing
                                 * (outputted on the sinks) */

  /* properties */
  gchar *uri;
  gchar *suburi;

  /* The currently outputted group_id */
  guint group_id;

  /* Bit-wise set of stream types we have requested from uridecodebin3 */
  GstStreamType selected_stream_types;

  /* Bit-wise set of stream types for which pads are present */
  GstStreamType present_stream_types;

  /* TRUE if a 'about-to-finish' needs to be posted once we have
   * got source pads for all requested stream types
   *
   * FIXME : Move this logic to uridecodebin3 later */
  gboolean pending_about_to_finish;

  /* uridecodebin to handle uri and suburi */
  GstElement *uridecodebin;

  /* Active sinks for each media type. These are initialized with
   * the configured or currently used sink, otherwise
   * left as NULL and playbin tries to automatically
   * select a good sink */
  GstElement *audio_sink;
  GstElement *video_sink;
  GstElement *text_sink;

  /* List of source pads */
  GList *source_pads;

  /* uridecodebin signals */
  gulong pad_added_id;
  gulong pad_removed_id;
  gulong select_stream_id;
  gulong source_setup_id;
  gulong about_to_finish_id;

#if 0                           /* AUTOPLUG DISABLED */
  gulong autoplug_factories_id;
  gulong autoplug_select_id;
  gulong autoplug_continue_id;
  gulong autoplug_query_id;
#endif

  gboolean stream_changed_pending;

  /* Active stream collection */
  GstStreamCollection *collection;


  /* buffering message stored for after switching */
  GstMessage *pending_buffering_msg;
};

#define GST_PLAY_BIN3_GET_LOCK(bin) (&((GstPlayBin3*)(bin))->lock)
#define GST_PLAY_BIN3_LOCK(bin) (g_rec_mutex_lock (GST_PLAY_BIN3_GET_LOCK(bin)))
#define GST_PLAY_BIN3_UNLOCK(bin) (g_rec_mutex_unlock (GST_PLAY_BIN3_GET_LOCK(bin)))

/* lock to protect dynamic callbacks, like no-more-pads */
#define GST_PLAY_BIN3_DYN_LOCK(bin)    g_mutex_lock (&(bin)->dyn_lock)
#define GST_PLAY_BIN3_DYN_UNLOCK(bin)  g_mutex_unlock (&(bin)->dyn_lock)

/* lock for shutdown */
#define GST_PLAY_BIN3_SHUTDOWN_LOCK(bin,label)			\
  G_STMT_START {						\
    if (G_UNLIKELY (g_atomic_int_get (&bin->shutdown)))		\
      goto label;						\
    GST_PLAY_BIN3_DYN_LOCK (bin);				\
    if (G_UNLIKELY (g_atomic_int_get (&bin->shutdown))) {	\
      GST_PLAY_BIN3_DYN_UNLOCK (bin);				\
      goto label;						\
    }								\
  } G_STMT_END

/* unlock for shutdown */
#define GST_PLAY_BIN3_SHUTDOWN_UNLOCK(bin)	\
  GST_PLAY_BIN3_DYN_UNLOCK (bin);		\

/**
 * GstPlayBin3:
 *
 * playbin element structure
 */
struct _GstPlayBin3
{
  GstPipeline parent;

  GRecMutex lock;               /* to protect group switching */

  /* the input groups, we use a double buffer to switch between current and next */
  GstSourceGroup groups[2];     /* array with group info */
  GstSourceGroup *curr_group;   /* pointer to the currently playing group */
  GstSourceGroup *next_group;   /* pointer to the next group */

  /* Array of GstPad controlled by each combiner */
  GPtrArray *channels[PLAYBIN_STREAM_LAST];     /* links to combiner pads */

  /* combiners for different streams */
  GstSourceCombine combiner[PLAYBIN_STREAM_LAST];

  /* Bit-wise set of stream types we have requested from uridecodebin3.
   * Calculated as the combination of the 'selected_stream_types' of
   * each sourcegroup */
  GstStreamType selected_stream_types;

  /* Bit-wise set of configured output stream types (i.e. active
     playsink inputs and combiners) */
  GstStreamType active_stream_types;

  /* properties */
  guint64 connection_speed;     /* connection speed in bits/sec (0 = unknown) */
  gint current_video;           /* the currently selected stream */
  gint current_audio;           /* the currently selected stream */
  gint current_text;            /* the currently selected stream */

  gboolean do_stream_selections;        /* Set to TRUE when any of current-{video|audio|text} are set to
                                           say playbin should do backwards-compatibility behaviours */

  guint64 buffer_duration;      /* When buffering, the max buffer duration (ns) */
  guint buffer_size;            /* When buffering, the max buffer size (bytes) */
  gboolean force_aspect_ratio;

  /* Multiview/stereoscopic overrides */
  GstVideoMultiviewFramePacking multiview_mode;
  GstVideoMultiviewFlags multiview_flags;

  /* our play sink */
  GstPlaySink *playsink;

  /* Task for (de)activating groups, protected by the activation lock */
  GstTask *activation_task;
  GRecMutex activation_lock;

  /* lock protecting dynamic adding/removing */
  GMutex dyn_lock;
  /* if we are shutting down or not */
  gint shutdown;
  gboolean async_pending;       /* async-start has been emitted */

  GMutex elements_lock;
  guint32 elements_cookie;
  GList *elements;              /* factories we can use for selecting elements */

  gboolean have_selector;       /* set to FALSE when we fail to create an
                                 * input-selector, so that we only post a
                                 * warning once */

  gboolean video_pending_flush_finish;  /* whether we are pending to send a custom
                                         * custom-video-flush-finish event
                                         * on pad activation */
  gboolean audio_pending_flush_finish;  /* whether we are pending to send a custom
                                         * custom-audio-flush-finish event
                                         * on pad activation */
  gboolean text_pending_flush_finish;   /* whether we are pending to send a custom
                                         * custom-subtitle-flush-finish event
                                         * on pad activation */

  GstElement *audio_sink;       /* configured audio sink, or NULL      */
  GstElement *video_sink;       /* configured video sink, or NULL      */
  GstElement *text_sink;        /* configured text sink, or NULL       */

  GstElement *audio_stream_combiner;    /* configured audio stream combiner, or NULL */
  GstElement *video_stream_combiner;    /* configured video stream combiner, or NULL */
  GstElement *text_stream_combiner;     /* configured text stream combiner, or NULL */

  GSequence *aelements;         /* a list of GstAVElements for audio stream */
  GSequence *velements;         /* a list of GstAVElements for video stream */

  guint64 ring_buffer_max_size; /* 0 means disabled */
};

struct _GstPlayBin3Class
{
  GstPipelineClass parent_class;

  /* notify app that the current uri finished decoding and it is possible to
   * queue a new one for gapless playback */
  void (*about_to_finish) (GstPlayBin3 * playbin);

  /* get the last video sample and convert it to the given caps */
  GstSample *(*convert_sample) (GstPlayBin3 * playbin, GstCaps * caps);
};

/* props */
#define DEFAULT_URI               NULL
#define DEFAULT_SUBURI            NULL
#define DEFAULT_FLAGS             GST_PLAY_FLAG_AUDIO | GST_PLAY_FLAG_VIDEO | GST_PLAY_FLAG_TEXT | \
                                  GST_PLAY_FLAG_SOFT_VOLUME | GST_PLAY_FLAG_DEINTERLACE | \
                                  GST_PLAY_FLAG_SOFT_COLORBALANCE | GST_PLAY_FLAG_BUFFERING
#define DEFAULT_CURRENT_VIDEO     -1
#define DEFAULT_CURRENT_AUDIO     -1
#define DEFAULT_CURRENT_TEXT      -1
#define DEFAULT_SUBTITLE_ENCODING NULL
#define DEFAULT_AUDIO_SINK        NULL
#define DEFAULT_VIDEO_SINK        NULL
#define DEFAULT_VIS_PLUGIN        NULL
#define DEFAULT_TEXT_SINK         NULL
#define DEFAULT_VOLUME            1.0
#define DEFAULT_MUTE              FALSE
#define DEFAULT_FRAME             NULL
#define DEFAULT_FONT_DESC         NULL
#define DEFAULT_CONNECTION_SPEED  0
#define DEFAULT_BUFFER_DURATION   -1
#define DEFAULT_BUFFER_SIZE       -1
#define DEFAULT_RING_BUFFER_MAX_SIZE 0

enum
{
  PROP_0,
  PROP_URI,
  PROP_CURRENT_URI,
  PROP_SUBURI,
  PROP_CURRENT_SUBURI,
  PROP_FLAGS,
  PROP_SUBTITLE_ENCODING,
  PROP_AUDIO_SINK,
  PROP_VIDEO_SINK,
  PROP_VIS_PLUGIN,
  PROP_TEXT_SINK,
  PROP_VIDEO_STREAM_COMBINER,
  PROP_AUDIO_STREAM_COMBINER,
  PROP_TEXT_STREAM_COMBINER,
  PROP_VOLUME,
  PROP_MUTE,
  PROP_SAMPLE,
  PROP_FONT_DESC,
  PROP_CONNECTION_SPEED,
  PROP_BUFFER_SIZE,
  PROP_BUFFER_DURATION,
  PROP_AV_OFFSET,
  PROP_RING_BUFFER_MAX_SIZE,
  PROP_FORCE_ASPECT_RATIO,
  PROP_AUDIO_FILTER,
  PROP_VIDEO_FILTER,
  PROP_MULTIVIEW_MODE,
  PROP_MULTIVIEW_FLAGS
};

/* signals */
enum
{
  SIGNAL_ABOUT_TO_FINISH,
  SIGNAL_CONVERT_SAMPLE,
  SIGNAL_SOURCE_SETUP,
  SIGNAL_ELEMENT_SETUP,
  LAST_SIGNAL
};

#if 0                           /* AUTOPLUG DISABLED */
static GstStaticCaps raw_audio_caps = GST_STATIC_CAPS ("audio/x-raw(ANY)");
static GstStaticCaps raw_video_caps = GST_STATIC_CAPS ("video/x-raw(ANY)");
#endif

static void gst_play_bin3_class_init (GstPlayBin3Class * klass);
static void gst_play_bin3_init (GstPlayBin3 * playbin);
static void gst_play_bin3_finalize (GObject * object);

static void gst_play_bin3_set_property (GObject * object, guint prop_id,
    const GValue * value, GParamSpec * spec);
static void gst_play_bin3_get_property (GObject * object, guint prop_id,
    GValue * value, GParamSpec * spec);

static GstStateChangeReturn gst_play_bin3_change_state (GstElement * element,
    GstStateChange transition);

static void gst_play_bin3_handle_message (GstBin * bin, GstMessage * message);
static void gst_play_bin3_deep_element_added (GstBin * playbin,
    GstBin * sub_bin, GstElement * child);
static gboolean gst_play_bin3_send_event (GstElement * element,
    GstEvent * event);

static GstSample *gst_play_bin3_convert_sample (GstPlayBin3 * playbin,
    GstCaps * caps);

static GstStateChangeReturn setup_next_source (GstPlayBin3 * playbin);

static void gst_play_bin3_check_group_status (GstPlayBin3 * playbin);
static void emit_about_to_finish (GstPlayBin3 * playbin);
static void reconfigure_output (GstPlayBin3 * playbin);
static void pad_removed_cb (GstElement * decodebin, GstPad * pad,
    GstSourceGroup * group);

static gint select_stream_cb (GstElement * decodebin,
    GstStreamCollection * collection, GstStream * stream,
    GstSourceGroup * group);

static void do_stream_selection (GstPlayBin3 * playbin, GstSourceGroup * group);

static GstElementClass *parent_class;

static guint gst_play_bin3_signals[LAST_SIGNAL] = { 0 };

#define REMOVE_SIGNAL(obj,id)			\
  if (id) {					\
    g_signal_handler_disconnect (obj, id);	\
    id = 0;					\
  }

static void gst_play_bin3_overlay_init (gpointer g_iface,
    gpointer g_iface_data);
static void gst_play_bin3_navigation_init (gpointer g_iface,
    gpointer g_iface_data);
static void gst_play_bin3_colorbalance_init (gpointer g_iface,
    gpointer g_iface_data);

static GType
gst_play_bin3_get_type (void)
{
  static GType gst_play_bin3_type = 0;

  if (!gst_play_bin3_type) {
    static const GTypeInfo gst_play_bin3_info = {
      sizeof (GstPlayBin3Class),
      NULL,
      NULL,
      (GClassInitFunc) gst_play_bin3_class_init,
      NULL,
      NULL,
      sizeof (GstPlayBin3),
      0,
      (GInstanceInitFunc) gst_play_bin3_init,
      NULL
    };
    static const GInterfaceInfo svol_info = {
      NULL, NULL, NULL
    };
    static const GInterfaceInfo ov_info = {
      gst_play_bin3_overlay_init,
      NULL, NULL
    };
    static const GInterfaceInfo nav_info = {
      gst_play_bin3_navigation_init,
      NULL, NULL
    };
    static const GInterfaceInfo col_info = {
      gst_play_bin3_colorbalance_init,
      NULL, NULL
    };

    gst_play_bin3_type = g_type_register_static (GST_TYPE_PIPELINE,
        "GstPlayBin3", &gst_play_bin3_info, 0);

    g_type_add_interface_static (gst_play_bin3_type, GST_TYPE_STREAM_VOLUME,
        &svol_info);
    g_type_add_interface_static (gst_play_bin3_type, GST_TYPE_VIDEO_OVERLAY,
        &ov_info);
    g_type_add_interface_static (gst_play_bin3_type, GST_TYPE_NAVIGATION,
        &nav_info);
    g_type_add_interface_static (gst_play_bin3_type, GST_TYPE_COLOR_BALANCE,
        &col_info);
  }

  return gst_play_bin3_type;
}

static void
gst_play_bin3_class_init (GstPlayBin3Class * klass)
{
  GObjectClass *gobject_klass;
  GstElementClass *gstelement_klass;
  GstBinClass *gstbin_klass;

  gobject_klass = (GObjectClass *) klass;
  gstelement_klass = (GstElementClass *) klass;
  gstbin_klass = (GstBinClass *) klass;

  parent_class = g_type_class_peek_parent (klass);

  gobject_klass->set_property = gst_play_bin3_set_property;
  gobject_klass->get_property = gst_play_bin3_get_property;

  gobject_klass->finalize = gst_play_bin3_finalize;

  /**
   * GstPlayBin3:uri
   *
   * Set the next URI that playbin will play. This property can be set from the
   * about-to-finish signal to queue the next media file.
   */
  g_object_class_install_property (gobject_klass, PROP_URI,
      g_param_spec_string ("uri", "URI", "URI of the media to play",
          NULL, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));

  /**
   * GstPlayBin3:current-uri
   *
   * The currently playing uri.
   */
  g_object_class_install_property (gobject_klass, PROP_CURRENT_URI,
      g_param_spec_string ("current-uri", "Current URI",
          "The currently playing URI", NULL,
          G_PARAM_READABLE | G_PARAM_STATIC_STRINGS));

  /**
   * GstPlayBin3:suburi
   *
   * Set the next subtitle URI that playbin will play. This property can be
   * set from the about-to-finish signal to queue the next subtitle media file.
   */
  g_object_class_install_property (gobject_klass, PROP_SUBURI,
      g_param_spec_string ("suburi", ".sub-URI", "Optional URI of a subtitle",
          NULL, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));

  /**
   * GstPlayBin3:current-suburi
   *
   * The currently playing subtitle uri.
   */
  g_object_class_install_property (gobject_klass, PROP_CURRENT_SUBURI,
      g_param_spec_string ("current-suburi", "Current .sub-URI",
          "The currently playing URI of a subtitle",
          NULL, G_PARAM_READABLE | G_PARAM_STATIC_STRINGS));

  /**
   * GstPlayBin3:flags
   *
   * Control the behaviour of playbin.
   */
  g_object_class_install_property (gobject_klass, PROP_FLAGS,
      g_param_spec_flags ("flags", "Flags", "Flags to control behaviour",
          GST_TYPE_PLAY_FLAGS, DEFAULT_FLAGS,
          G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));

  g_object_class_install_property (gobject_klass, PROP_SUBTITLE_ENCODING,
      g_param_spec_string ("subtitle-encoding", "subtitle encoding",
          "Encoding to assume if input subtitles are not in UTF-8 encoding. "
          "If not set, the GST_SUBTITLE_ENCODING environment variable will "
          "be checked for an encoding to use. If that is not set either, "
          "ISO-8859-15 will be assumed.", NULL,
          G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));

  g_object_class_install_property (gobject_klass, PROP_VIDEO_FILTER,
      g_param_spec_object ("video-filter", "Video filter",
          "the video filter(s) to apply, if possible",
          GST_TYPE_ELEMENT, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
  g_object_class_install_property (gobject_klass, PROP_AUDIO_FILTER,
      g_param_spec_object ("audio-filter", "Audio filter",
          "the audio filter(s) to apply, if possible",
          GST_TYPE_ELEMENT, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
  /**
   * GstPlayBin3:video-sink
   *
   * Get or set the video sink to use for video output. If set to
   * NULL, one will be auto-selected. To disable video entirely, unset
   * the VIDEO flag in the #GstPlayBin3:flags property.
   *
   */
  g_object_class_install_property (gobject_klass, PROP_VIDEO_SINK,
      g_param_spec_object ("video-sink", "Video Sink",
          "the video output element to use (NULL = default sink)",
          GST_TYPE_ELEMENT, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
  /**
   * GstPlayBin3:audio-sink
   *
   * Get or set the audio sink to use for audio output. If set to
   * NULL, one will be auto-selected. To disable audio entirely, unset
   * the AUDIO flag in the #GstPlayBin3:flags property.
   *
   */
  g_object_class_install_property (gobject_klass, PROP_AUDIO_SINK,
      g_param_spec_object ("audio-sink", "Audio Sink",
          "the audio output element to use (NULL = default sink)",
          GST_TYPE_ELEMENT, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
  g_object_class_install_property (gobject_klass, PROP_VIS_PLUGIN,
      g_param_spec_object ("vis-plugin", "Vis plugin",
          "the visualization element to use (NULL = default)",
          GST_TYPE_ELEMENT, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
  g_object_class_install_property (gobject_klass, PROP_TEXT_SINK,
      g_param_spec_object ("text-sink", "Text plugin",
          "the text output element to use (NULL = default subtitleoverlay)",
          GST_TYPE_ELEMENT, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
  /**
   * GstPlayBin3:video-stream-combiner
   *
   * Get or set the current video stream combiner. By default, no
   * element is used and the selected stream is used directly.
   */
  g_object_class_install_property (gobject_klass, PROP_VIDEO_STREAM_COMBINER,
      g_param_spec_object ("video-stream-combiner", "Video stream combiner",
          "Current video stream combiner (default: none)",
          GST_TYPE_ELEMENT, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));

  /**
   * GstPlayBin3:audio-stream-combiner
   *
   * Get or set the current audio stream combiner. By default, no
   * element is used and the selected stream is used directly.
   */
  g_object_class_install_property (gobject_klass, PROP_AUDIO_STREAM_COMBINER,
      g_param_spec_object ("audio-stream-combiner", "Audio stream combiner",
          "Current audio stream combiner (default: none))",
          GST_TYPE_ELEMENT, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));

  /**
   * GstPlayBin3:text-stream-combiner
   *
   * Get or set the current text stream combiner. By default, no
   * element is used and the selected stream is used directly.
   */
  g_object_class_install_property (gobject_klass, PROP_TEXT_STREAM_COMBINER,
      g_param_spec_object ("text-stream-combiner", "Text stream combiner",
          "Current text stream combiner (default: none)",
          GST_TYPE_ELEMENT, G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));

  /**
   * GstPlayBin3:volume:
   *
   * Get or set the current audio stream volume. 1.0 means 100%,
   * 0.0 means mute. This uses a linear volume scale.
   *
   */
  g_object_class_install_property (gobject_klass, PROP_VOLUME,
      g_param_spec_double ("volume", "Volume", "The audio volume, 1.0=100%",
          0.0, VOLUME_MAX_DOUBLE, 1.0,
          G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
  g_object_class_install_property (gobject_klass, PROP_MUTE,
      g_param_spec_boolean ("mute", "Mute",
          "Mute the audio channel without changing the volume", FALSE,
          G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));

  /**
   * GstPlayBin3:sample:
   * @playbin: a #GstPlayBin3
   *
   * Get the currently rendered or prerolled sample in the video sink.
   * The #GstCaps in the sample will describe the format of the buffer.
   */
  g_object_class_install_property (gobject_klass, PROP_SAMPLE,
      g_param_spec_boxed ("sample", "Sample",
          "The last sample (NULL = no video available)",
          GST_TYPE_SAMPLE, G_PARAM_READABLE | G_PARAM_STATIC_STRINGS));

  g_object_class_install_property (gobject_klass, PROP_FONT_DESC,
      g_param_spec_string ("subtitle-font-desc",
          "Subtitle font description",
          "Pango font description of font "
          "to be used for subtitle rendering", NULL,
          G_PARAM_WRITABLE | G_PARAM_STATIC_STRINGS));

  g_object_class_install_property (gobject_klass, PROP_CONNECTION_SPEED,
      g_param_spec_uint64 ("connection-speed", "Connection Speed",
          "Network connection speed in kbps (0 = unknown)",
          0, G_MAXUINT64 / 1000, DEFAULT_CONNECTION_SPEED,
          G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));

  g_object_class_install_property (gobject_klass, PROP_BUFFER_SIZE,
      g_param_spec_int ("buffer-size", "Buffer size (bytes)",
          "Buffer size when buffering network streams",
          -1, G_MAXINT, DEFAULT_BUFFER_SIZE,
          G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
  g_object_class_install_property (gobject_klass, PROP_BUFFER_DURATION,
      g_param_spec_int64 ("buffer-duration", "Buffer duration (ns)",
          "Buffer duration when buffering network streams",
          -1, G_MAXINT64, DEFAULT_BUFFER_DURATION,
          G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));
  /**
   * GstPlayBin3:av-offset:
   *
   * Control the synchronisation offset between the audio and video streams.
   * Positive values make the audio ahead of the video and negative values make
   * the audio go behind the video.
   */
  g_object_class_install_property (gobject_klass, PROP_AV_OFFSET,
      g_param_spec_int64 ("av-offset", "AV Offset",
          "The synchronisation offset between audio and video in nanoseconds",
          G_MININT64, G_MAXINT64, 0,
          G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));

  /**
   * GstPlayBin3:ring-buffer-max-size
   *
   * The maximum size of the ring buffer in bytes. If set to 0, the ring
   * buffer is disabled. Default 0.
   */
  g_object_class_install_property (gobject_klass, PROP_RING_BUFFER_MAX_SIZE,
      g_param_spec_uint64 ("ring-buffer-max-size",
          "Max. ring buffer size (bytes)",
          "Max. amount of data in the ring buffer (bytes, 0 = ring buffer disabled)",
          0, G_MAXUINT, DEFAULT_RING_BUFFER_MAX_SIZE,
          G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));

  /**
   * GstPlayBin3::force-aspect-ratio:
   *
   * Requests the video sink to enforce the video display aspect ratio.
   */
  g_object_class_install_property (gobject_klass, PROP_FORCE_ASPECT_RATIO,
      g_param_spec_boolean ("force-aspect-ratio", "Force Aspect Ratio",
          "When enabled, scaling will respect original aspect ratio", TRUE,
          G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));

  /**
   * GstPlayBin3::video-multiview-mode:
   *
   * Set the stereoscopic mode for video streams that don't contain
   * any information in the stream, so they can be correctly played
   * as 3D streams. If a video already has multiview information
   * encoded, this property can override other modes in the set,
   * but cannot be used to re-interpret MVC or mixed-mono streams.
   *
   * See Also: The #GstPlayBin3::video-multiview-flags property
   *
   */
  g_object_class_install_property (gobject_klass, PROP_MULTIVIEW_MODE,
      g_param_spec_enum ("video-multiview-mode",
          "Multiview Mode Override",
          "Re-interpret a video stream as one of several frame-packed stereoscopic modes.",
          GST_TYPE_VIDEO_MULTIVIEW_FRAME_PACKING,
          GST_VIDEO_MULTIVIEW_FRAME_PACKING_NONE,
          G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));

  /**
   * GstPlayBin3::video-multiview-flags:
   *
   * When overriding the multiview mode of an input stream,
   * these flags modify details of the view layout.
   *
   * See Also: The #GstPlayBin3::video-multiview-mode property
   */
  g_object_class_install_property (gobject_klass, PROP_MULTIVIEW_FLAGS,
      g_param_spec_flags ("video-multiview-flags",
          "Multiview Flags Override",
          "Override details of the multiview frame layout",
          GST_TYPE_VIDEO_MULTIVIEW_FLAGS, GST_VIDEO_MULTIVIEW_FLAGS_NONE,
          G_PARAM_READWRITE | G_PARAM_STATIC_STRINGS));

  /**
   * GstPlayBin3::about-to-finish
   * @playbin: a #GstPlayBin3
   *
   * This signal is emitted when the current uri is about to finish. You can
   * set the uri and suburi to make sure that playback continues.
   *
   * This signal is emitted from the context of a GStreamer streaming thread.
   */
  gst_play_bin3_signals[SIGNAL_ABOUT_TO_FINISH] =
      g_signal_new ("about-to-finish", G_TYPE_FROM_CLASS (klass),
      G_SIGNAL_RUN_LAST,
      G_STRUCT_OFFSET (GstPlayBin3Class, about_to_finish), NULL, NULL,
      g_cclosure_marshal_generic, G_TYPE_NONE, 0, G_TYPE_NONE);


  /**
   * GstPlayBin3::source-setup:
   * @playbin: a #GstPlayBin3
   * @source: source element
   *
   * This signal is emitted after the source element has been created, so
   * it can be configured by setting additional properties (e.g. set a
   * proxy server for an http source, or set the device and read speed for
   * an audio cd source). This is functionally equivalent to connecting to
   * the notify::source signal, but more convenient.
   *
   * This signal is usually emitted from the context of a GStreamer streaming
   * thread.
   */
  gst_play_bin3_signals[SIGNAL_SOURCE_SETUP] =
      g_signal_new ("source-setup", G_TYPE_FROM_CLASS (klass),
      G_SIGNAL_RUN_LAST, 0, NULL, NULL,
      g_cclosure_marshal_generic, G_TYPE_NONE, 1, GST_TYPE_ELEMENT);

  /**
   * GstPlayBin3::element-setup:
   * @playbin: a #GstPlayBin3
   * @element: an element that was added to the playbin hierarchy
   *
   * This signal is emitted when a new element is added to playbin or any of
   * its sub-bins. This signal can be used to configure elements, e.g. to set
   * properties on decoders. This is functionally equivalent to connecting to
   * the deep-element-added signal, but more convenient.
   *
   * This signal is usually emitted from the context of a GStreamer streaming
   * thread, so might be called at the same time as code running in the main
   * application thread.
   *
   * Since: 1.10
   */
  gst_play_bin3_signals[SIGNAL_ELEMENT_SETUP] =
      g_signal_new ("element-setup", G_TYPE_FROM_CLASS (klass),
      G_SIGNAL_RUN_LAST, 0, NULL, NULL,
      g_cclosure_marshal_generic, G_TYPE_NONE, 1, GST_TYPE_ELEMENT);

  /**
   * GstPlayBin3::convert-sample
   * @playbin: a #GstPlayBin3
   * @caps: the target format of the frame
   *
   * Action signal to retrieve the currently playing video frame in the format
   * specified by @caps.
   * If @caps is %NULL, no conversion will be performed and this function is
   * equivalent to the #GstPlayBin3::sample property.
   *
   * Returns: a #GstSample of the current video frame converted to #caps.
   * The caps on the sample will describe the final layout of the buffer data.
   * %NULL is returned when no current buffer can be retrieved or when the
   * conversion failed.
   */
  gst_play_bin3_signals[SIGNAL_CONVERT_SAMPLE] =
      g_signal_new ("convert-sample", G_TYPE_FROM_CLASS (klass),
      G_SIGNAL_RUN_LAST | G_SIGNAL_ACTION,
      G_STRUCT_OFFSET (GstPlayBin3Class, convert_sample), NULL, NULL,
      g_cclosure_marshal_generic, GST_TYPE_SAMPLE, 1, GST_TYPE_CAPS);

  klass->convert_sample = gst_play_bin3_convert_sample;

  gst_element_class_set_static_metadata (gstelement_klass,
      "Player Bin 3", "Generic/Bin/Player",
      "Autoplug and play media from an uri",
      "Wim Taymans <wim.taymans@gmail.com>");

  gstelement_klass->change_state =
      GST_DEBUG_FUNCPTR (gst_play_bin3_change_state);
  gstelement_klass->send_event = GST_DEBUG_FUNCPTR (gst_play_bin3_send_event);

  gstbin_klass->handle_message =
      GST_DEBUG_FUNCPTR (gst_play_bin3_handle_message);
  gstbin_klass->deep_element_added =
      GST_DEBUG_FUNCPTR (gst_play_bin3_deep_element_added);
}

static void
do_async_start (GstPlayBin3 * playbin)
{
  GstMessage *message;

  playbin->async_pending = TRUE;

  message = gst_message_new_async_start (GST_OBJECT_CAST (playbin));
  GST_BIN_CLASS (parent_class)->handle_message (GST_BIN_CAST (playbin),
      message);
}

static void
do_async_done (GstPlayBin3 * playbin)
{
  GstMessage *message;

  if (playbin->async_pending) {
    GST_DEBUG_OBJECT (playbin, "posting ASYNC_DONE");
    message =
        gst_message_new_async_done (GST_OBJECT_CAST (playbin),
        GST_CLOCK_TIME_NONE);
    GST_BIN_CLASS (parent_class)->handle_message (GST_BIN_CAST (playbin),
        message);

    playbin->async_pending = FALSE;
  }
}

/* init combiners. The combiner is found by finding the first prefix that
 * matches the media. */
static void
init_combiners (GstPlayBin3 * playbin)
{
  gint i;

  /* store the array for the different channels */
  for (i = 0; i < PLAYBIN_STREAM_LAST; i++)
    playbin->channels[i] = g_ptr_array_new ();

  playbin->combiner[PLAYBIN_STREAM_AUDIO].media_type = "audio";
  playbin->combiner[PLAYBIN_STREAM_AUDIO].type = GST_PLAY_SINK_TYPE_AUDIO;
  playbin->combiner[PLAYBIN_STREAM_AUDIO].stream_type = GST_STREAM_TYPE_AUDIO;
  playbin->combiner[PLAYBIN_STREAM_AUDIO].channels = playbin->channels[0];
  playbin->combiner[PLAYBIN_STREAM_AUDIO].streams =
      g_ptr_array_new_with_free_func ((GDestroyNotify) gst_object_unref);

  playbin->combiner[PLAYBIN_STREAM_VIDEO].media_type = "video";
  playbin->combiner[PLAYBIN_STREAM_VIDEO].type = GST_PLAY_SINK_TYPE_VIDEO;
  playbin->combiner[PLAYBIN_STREAM_VIDEO].stream_type = GST_STREAM_TYPE_VIDEO;
  playbin->combiner[PLAYBIN_STREAM_VIDEO].channels = playbin->channels[1];
  playbin->combiner[PLAYBIN_STREAM_VIDEO].streams =
      g_ptr_array_new_with_free_func ((GDestroyNotify) gst_object_unref);

  playbin->combiner[PLAYBIN_STREAM_TEXT].media_type = "text";
  playbin->combiner[PLAYBIN_STREAM_TEXT].get_media_caps =
      gst_subtitle_overlay_create_factory_caps;
  playbin->combiner[PLAYBIN_STREAM_TEXT].type = GST_PLAY_SINK_TYPE_TEXT;
  playbin->combiner[PLAYBIN_STREAM_TEXT].stream_type = GST_STREAM_TYPE_TEXT;
  playbin->combiner[PLAYBIN_STREAM_TEXT].channels = playbin->channels[2];
  playbin->combiner[PLAYBIN_STREAM_TEXT].streams =
      g_ptr_array_new_with_free_func ((GDestroyNotify) gst_object_unref);
}

/* Update the combiner information to be in sync with the current collection
 *
 * FIXME : "current" collection doesn't mean anything until we have a "combined"
 *  collection of all groups */
static void
update_combiner_info (GstPlayBin3 * playbin, GstStreamCollection * collection)
{
  guint i, len;

  if (collection == NULL)
    return;

  GST_DEBUG_OBJECT (playbin, "Updating combiner info");

  /* Wipe current combiner streams */
  g_ptr_array_free (playbin->combiner[PLAYBIN_STREAM_AUDIO].streams, TRUE);
  g_ptr_array_free (playbin->combiner[PLAYBIN_STREAM_VIDEO].streams, TRUE);
  g_ptr_array_free (playbin->combiner[PLAYBIN_STREAM_TEXT].streams, TRUE);
  playbin->combiner[PLAYBIN_STREAM_AUDIO].streams =
      g_ptr_array_new_with_free_func ((GDestroyNotify) gst_object_unref);
  playbin->combiner[PLAYBIN_STREAM_VIDEO].streams =
      g_ptr_array_new_with_free_func ((GDestroyNotify) gst_object_unref);
  playbin->combiner[PLAYBIN_STREAM_TEXT].streams =
      g_ptr_array_new_with_free_func ((GDestroyNotify) gst_object_unref);

  len = gst_stream_collection_get_size (collection);
  for (i = 0; i < len; i++) {
    GstStream *stream = gst_stream_collection_get_stream (collection, i);
    GstStreamType stype = gst_stream_get_stream_type (stream);

    if (stype & GST_STREAM_TYPE_AUDIO) {
      g_ptr_array_add (playbin->combiner[PLAYBIN_STREAM_AUDIO].streams,
          gst_object_ref (stream));
    } else if (stype & GST_STREAM_TYPE_VIDEO) {
      g_ptr_array_add (playbin->combiner[PLAYBIN_STREAM_VIDEO].streams,
          gst_object_ref (stream));
    } else if (stype & GST_STREAM_TYPE_TEXT) {
      g_ptr_array_add (playbin->combiner[PLAYBIN_STREAM_TEXT].streams,
          gst_object_ref (stream));
    }
  }

  GST_DEBUG_OBJECT (playbin, "There are %d audio streams",
      playbin->combiner[PLAYBIN_STREAM_AUDIO].streams->len);
  GST_DEBUG_OBJECT (playbin, "There are %d video streams",
      playbin->combiner[PLAYBIN_STREAM_VIDEO].streams->len);
  GST_DEBUG_OBJECT (playbin, "There are %d text streams",
      playbin->combiner[PLAYBIN_STREAM_TEXT].streams->len);
}

#ifndef GST_DISABLE_GST_DEBUG
#define debug_groups(playbin) G_STMT_START {	\
    guint i;					\
    						\
    for (i = 0; i < 2; i++) {				\
      GstSourceGroup *group = &playbin->groups[i];	\
      							\
      GST_DEBUG ("GstSourceGroup #%d (%s)", i, (group == playbin->curr_group) ? "current" : (group == playbin->next_group) ? "next" : "unused"); \
      GST_DEBUG ("  valid:%d , active:%d , playing:%d", group->valid, group->active, group->playing); \
      GST_DEBUG ("  uri:%s", group->uri);				\
      GST_DEBUG ("  suburi:%s", group->suburi);				\
      GST_DEBUG ("  group_id:%d", group->group_id);			\
      GST_DEBUG ("  pending_about_to_finish:%d", group->pending_about_to_finish); \
    }									\
  } G_STMT_END
#else
#define debug_groups(p) {}
#endif

static void
init_group (GstPlayBin3 * playbin, GstSourceGroup * group)
{
  g_mutex_init (&group->lock);

  group->stream_changed_pending = FALSE;
  group->group_id = GST_GROUP_ID_INVALID;

  group->playbin = playbin;
}

static void
free_group (GstPlayBin3 * playbin, GstSourceGroup * group)
{
  g_free (group->uri);
  g_free (group->suburi);

  g_mutex_clear (&group->lock);
  group->stream_changed_pending = FALSE;

  if (group->pending_buffering_msg)
    gst_message_unref (group->pending_buffering_msg);
  group->pending_buffering_msg = NULL;

  gst_object_replace ((GstObject **) & group->collection, NULL);

  gst_object_replace ((GstObject **) & group->audio_sink, NULL);
  gst_object_replace ((GstObject **) & group->video_sink, NULL);
  gst_object_replace ((GstObject **) & group->text_sink, NULL);
}

static void
notify_volume_cb (GObject * combiner, GParamSpec * pspec, GstPlayBin3 * playbin)
{
  g_object_notify (G_OBJECT (playbin), "volume");
}

static void
notify_mute_cb (GObject * combiner, GParamSpec * pspec, GstPlayBin3 * playbin)
{
  g_object_notify (G_OBJECT (playbin), "mute");
}

static void
colorbalance_value_changed_cb (GstColorBalance * balance,
    GstColorBalanceChannel * channel, gint value, GstPlayBin3 * playbin)
{
  gst_color_balance_value_changed (GST_COLOR_BALANCE (playbin), channel, value);
}

#if 0                           /* AUTOPLUG DISABLED */
static gint
compare_factories_func (gconstpointer p1, gconstpointer p2)
{
  GstPluginFeature *f1, *f2;
  gboolean is_sink1, is_sink2;
  gboolean is_parser1, is_parser2;

  f1 = (GstPluginFeature *) p1;
  f2 = (GstPluginFeature *) p2;

  is_sink1 = gst_element_factory_list_is_type (GST_ELEMENT_FACTORY_CAST (f1),
      GST_ELEMENT_FACTORY_TYPE_SINK);
  is_sink2 = gst_element_factory_list_is_type (GST_ELEMENT_FACTORY_CAST (f2),
      GST_ELEMENT_FACTORY_TYPE_SINK);
  is_parser1 = gst_element_factory_list_is_type (GST_ELEMENT_FACTORY_CAST (f1),
      GST_ELEMENT_FACTORY_TYPE_PARSER);
  is_parser2 = gst_element_factory_list_is_type (GST_ELEMENT_FACTORY_CAST (f2),
      GST_ELEMENT_FACTORY_TYPE_PARSER);

  /* First we want all sinks as we prefer a sink if it directly
   * supports the current caps */
  if (is_sink1 && !is_sink2)
    return -1;
  else if (!is_sink1 && is_sink2)
    return 1;

  /* Then we want all parsers as we always want to plug parsers
   * before decoders */
  if (is_parser1 && !is_parser2)
    return -1;
  else if (!is_parser1 && is_parser2)
    return 1;

  /* And if it's a both a parser or sink we first sort by rank
   * and then by factory name */
  return gst_plugin_feature_rank_compare_func (p1, p2);
}

/* Must be called with elements lock! */
static void
gst_play_bin3_update_elements_list (GstPlayBin3 * playbin)
{
  GList *res, *tmp;
  guint cookie;

  cookie = gst_registry_get_feature_list_cookie (gst_registry_get ());

  if (!playbin->elements || playbin->elements_cookie != cookie) {
    if (playbin->elements)
      gst_plugin_feature_list_free (playbin->elements);
    res =
        gst_element_factory_list_get_elements
        (GST_ELEMENT_FACTORY_TYPE_DECODABLE, GST_RANK_MARGINAL);
    tmp =
        gst_element_factory_list_get_elements
        (GST_ELEMENT_FACTORY_TYPE_AUDIOVIDEO_SINKS, GST_RANK_MARGINAL);
    playbin->elements = g_list_concat (res, tmp);
    playbin->elements = g_list_sort (playbin->elements, compare_factories_func);
  }

  if (!playbin->aelements || playbin->elements_cookie != cookie) {
    if (playbin->aelements)
      g_sequence_free (playbin->aelements);
    playbin->aelements = avelements_create (playbin, TRUE);
  }

  if (!playbin->velements || playbin->elements_cookie != cookie) {
    if (playbin->velements)
      g_sequence_free (playbin->velements);
    playbin->velements = avelements_create (playbin, FALSE);
  }

  playbin->elements_cookie = cookie;
}
#endif

static void
gst_play_bin3_init (GstPlayBin3 * playbin)
{
  g_rec_mutex_init (&playbin->lock);
  g_mutex_init (&playbin->dyn_lock);

  /* assume we can create an input-selector */
  playbin->have_selector = TRUE;

  init_combiners (playbin);

  /* init groups */
  playbin->curr_group = &playbin->groups[0];
  playbin->next_group = &playbin->groups[1];
  init_group (playbin, &playbin->groups[0]);
  init_group (playbin, &playbin->groups[1]);

  /* first filter out the interesting element factories */
  g_mutex_init (&playbin->elements_lock);

  g_rec_mutex_init (&playbin->activation_lock);

  /* add sink */
  playbin->playsink =
      g_object_new (GST_TYPE_PLAY_SINK, "name", "playsink", "send-event-mode",
      1, NULL);
  gst_bin_add (GST_BIN_CAST (playbin), GST_ELEMENT_CAST (playbin->playsink));
  gst_play_sink_set_flags (playbin->playsink, DEFAULT_FLAGS);
  /* Connect to notify::volume and notify::mute signals for proxying */
  g_signal_connect (playbin->playsink, "notify::volume",
      G_CALLBACK (notify_volume_cb), playbin);
  g_signal_connect (playbin->playsink, "notify::mute",
      G_CALLBACK (notify_mute_cb), playbin);
  g_signal_connect (playbin->playsink, "value-changed",
      G_CALLBACK (colorbalance_value_changed_cb), playbin);

  playbin->current_video = DEFAULT_CURRENT_VIDEO;
  playbin->current_audio = DEFAULT_CURRENT_AUDIO;
  playbin->current_text = DEFAULT_CURRENT_TEXT;

  playbin->buffer_duration = DEFAULT_BUFFER_DURATION;
  playbin->buffer_size = DEFAULT_BUFFER_SIZE;
  playbin->ring_buffer_max_size = DEFAULT_RING_BUFFER_MAX_SIZE;

  playbin->force_aspect_ratio = TRUE;

  playbin->multiview_mode = GST_VIDEO_MULTIVIEW_FRAME_PACKING_NONE;
  playbin->multiview_flags = GST_VIDEO_MULTIVIEW_FLAGS_NONE;
}

static void
gst_play_bin3_finalize (GObject * object)
{
  GstPlayBin3 *playbin;
  gint i;

  playbin = GST_PLAY_BIN3 (object);

  free_group (playbin, &playbin->groups[0]);
  free_group (playbin, &playbin->groups[1]);

  for (i = 0; i < PLAYBIN_STREAM_LAST; i++)
    g_ptr_array_free (playbin->channels[i], TRUE);

  /* Setting states to NULL is safe here because playsink
   * will already be gone and none of these sinks will be
   * a child of playsink
   */
  if (playbin->video_sink) {
    gst_element_set_state (playbin->video_sink, GST_STATE_NULL);
    gst_object_unref (playbin->video_sink);
  }
  if (playbin->audio_sink) {
    gst_element_set_state (playbin->audio_sink, GST_STATE_NULL);
    gst_object_unref (playbin->audio_sink);
  }
  if (playbin->text_sink) {
    gst_element_set_state (playbin->text_sink, GST_STATE_NULL);
    gst_object_unref (playbin->text_sink);
  }

  if (playbin->video_stream_combiner) {
    gst_element_set_state (playbin->video_stream_combiner, GST_STATE_NULL);
    gst_object_unref (playbin->video_stream_combiner);
  }
  if (playbin->audio_stream_combiner) {
    gst_element_set_state (playbin->audio_stream_combiner, GST_STATE_NULL);
    gst_object_unref (playbin->audio_stream_combiner);
  }
  if (playbin->text_stream_combiner) {
    gst_element_set_state (playbin->text_stream_combiner, GST_STATE_NULL);
    gst_object_unref (playbin->text_stream_combiner);
  }

  g_ptr_array_free (playbin->combiner[PLAYBIN_STREAM_AUDIO].streams, TRUE);
  g_ptr_array_free (playbin->combiner[PLAYBIN_STREAM_VIDEO].streams, TRUE);
  g_ptr_array_free (playbin->combiner[PLAYBIN_STREAM_TEXT].streams, TRUE);

  if (playbin->elements)
    gst_plugin_feature_list_free (playbin->elements);

  if (playbin->aelements)
    g_sequence_free (playbin->aelements);

  if (playbin->velements)
    g_sequence_free (playbin->velements);

  g_rec_mutex_clear (&playbin->activation_lock);
  g_rec_mutex_clear (&playbin->lock);
  g_mutex_clear (&playbin->dyn_lock);
  g_mutex_clear (&playbin->elements_lock);

  G_OBJECT_CLASS (parent_class)->finalize (object);
}

static gboolean
gst_playbin_uri_is_valid (GstPlayBin3 * playbin, const gchar * uri)
{
  const gchar *c;

  GST_LOG_OBJECT (playbin, "checking uri '%s'", uri);

  /* this just checks the protocol */
  if (!gst_uri_is_valid (uri))
    return FALSE;

  for (c = uri; *c != '\0'; ++c) {
    if (!g_ascii_isprint (*c))
      goto invalid;
    if (*c == ' ')
      goto invalid;
  }

  return TRUE;

invalid:
  {
    GST_WARNING_OBJECT (playbin, "uri '%s' not valid, character #%u",
        uri, (guint) ((guintptr) c - (guintptr) uri));
    return FALSE;
  }
}

static void
gst_play_bin3_set_uri (GstPlayBin3 * playbin, const gchar * uri)
{
  GstSourceGroup *group;

  if (uri == NULL) {
    g_warning ("cannot set NULL uri");
    return;
  }

  if (!gst_playbin_uri_is_valid (playbin, uri)) {
    if (g_str_has_prefix (uri, "file:")) {
      GST_WARNING_OBJECT (playbin, "not entirely correct file URI '%s' - make "
          "sure to escape spaces and non-ASCII characters properly and specify "
          "an absolute path. Use gst_filename_to_uri() to convert filenames "
          "to URIs", uri);
    } else {
      /* GST_ERROR_OBJECT (playbin, "malformed URI '%s'", uri); */
    }
  }

  GST_PLAY_BIN3_LOCK (playbin);
  group = playbin->next_group;

  GST_SOURCE_GROUP_LOCK (group);
  /* store the uri in the next group we will play */
  g_free (group->uri);
  group->uri = g_strdup (uri);
  group->valid = TRUE;
  GST_SOURCE_GROUP_UNLOCK (group);

  GST_DEBUG ("set new uri to %s", uri);
  GST_PLAY_BIN3_UNLOCK (playbin);
}

static void
gst_play_bin3_set_suburi (GstPlayBin3 * playbin, const gchar * suburi)
{
  GstSourceGroup *group;

  GST_PLAY_BIN3_LOCK (playbin);
  group = playbin->next_group;

  GST_SOURCE_GROUP_LOCK (group);
  g_free (group->suburi);
  group->suburi = g_strdup (suburi);
  GST_SOURCE_GROUP_UNLOCK (group);

  GST_DEBUG ("setting new .sub uri to %s", suburi);

  GST_PLAY_BIN3_UNLOCK (playbin);
}

static void
gst_play_bin3_set_flags (GstPlayBin3 * playbin, GstPlayFlags flags)
{
  GstPlayFlags old_flags;
  old_flags = gst_play_sink_get_flags (playbin->playsink);

  if (flags != old_flags) {
    gst_play_sink_set_flags (playbin->playsink, flags);
    gst_play_sink_reconfigure (playbin->playsink);
  }
}

static GstPlayFlags
gst_play_bin3_get_flags (GstPlayBin3 * playbin)
{
  GstPlayFlags flags;

  flags = gst_play_sink_get_flags (playbin->playsink);

  return flags;
}

/* get the currently playing group or if nothing is playing, the next
 * group. Must be called with the PLAY_BIN_LOCK. */
static GstSourceGroup *
get_group (GstPlayBin3 * playbin)
{
  GstSourceGroup *result;

  if (!(result = playbin->curr_group))
    result = playbin->next_group;

  return result;
}


static GstSample *
gst_play_bin3_convert_sample (GstPlayBin3 * playbin, GstCaps * caps)
{
  return gst_play_sink_convert_sample (playbin->playsink, caps);
}

static gboolean
gst_play_bin3_send_custom_event (GstObject * combiner, const gchar * event_name)
{
  GstPad *src;
  GstPad *peer;
  GstStructure *s;
  GstEvent *event;
  gboolean ret = FALSE;

  src = gst_element_get_static_pad (GST_ELEMENT_CAST (combiner), "src");
  peer = gst_pad_get_peer (src);
  if (peer) {
    s = gst_structure_new_empty (event_name);
    event = gst_event_new_custom (GST_EVENT_CUSTOM_DOWNSTREAM_OOB, s);
    gst_pad_send_event (peer, event);
    gst_object_unref (peer);
    ret = TRUE;
  }
  gst_object_unref (src);
  return ret;
}

static gboolean
gst_play_bin3_set_current_stream (GstPlayBin3 * playbin,
    gint stream_type, gint * current_value, gint stream,
    gboolean * flush_marker)
{
  GstSourceCombine *combine;
  GPtrArray *channels;
  GstPad *sinkpad;

  GST_PLAY_BIN3_LOCK (playbin);
  /* This function is only called if the app sets
   * one of the current-* properties, which means it doesn't
   * handle collections or select-streams yet */
  playbin->do_stream_selections = TRUE;

  combine = playbin->combiner + stream_type;
  channels = playbin->channels[stream_type];

  GST_DEBUG_OBJECT (playbin, "Changing current %s stream %d -> %d",
      stream_type_names[stream_type], *current_value, stream);

  if (combine->combiner == NULL || combine->is_concat) {
    /* FIXME: Check that the current_value is within range */
    *current_value = stream;
    do_stream_selection (playbin, playbin->curr_group);
    GST_PLAY_BIN3_UNLOCK (playbin);
    return TRUE;
  }

  GST_DEBUG_OBJECT (playbin, "Using old style combiner");

  if (!combine->has_active_pad)
    goto no_active_pad;
  if (channels == NULL)
    goto no_channels;

  if (stream == -1 || channels->len <= stream) {
    sinkpad = NULL;
  } else {
    /* take channel from selected stream */
    sinkpad = g_ptr_array_index (channels, stream);
  }

  if (sinkpad)
    gst_object_ref (sinkpad);
  GST_PLAY_BIN3_UNLOCK (playbin);

  if (sinkpad) {
    GstObject *combiner;

    if ((combiner = gst_pad_get_parent (sinkpad))) {
      GstPad *old_sinkpad;

      g_object_get (combiner, "active-pad", &old_sinkpad, NULL);

      if (old_sinkpad != sinkpad) {
        /* FIXME: Is there actually any reason playsink
         * needs special names for each type of stream we flush? */
        gchar *flush_event_name = g_strdup_printf ("playsink-custom-%s-flush",
            stream_type_names[stream_type]);
        if (gst_play_bin3_send_custom_event (combiner, flush_event_name))
          *flush_marker = TRUE;
        g_free (flush_event_name);

        /* activate the selected pad */
        g_object_set (combiner, "active-pad", sinkpad, NULL);
      }

      if (old_sinkpad)
        gst_object_unref (old_sinkpad);

      gst_object_unref (combiner);
    }
    gst_object_unref (sinkpad);
  }
  return TRUE;

no_active_pad:
  {
    GST_PLAY_BIN3_UNLOCK (playbin);
    GST_WARNING_OBJECT (playbin,
        "can't switch %s, the stream combiner's sink pads don't have the \"active-pad\" property",
        stream_type_names[stream_type]);
    return FALSE;
  }
no_channels:
  {
    GST_PLAY_BIN3_UNLOCK (playbin);
    GST_DEBUG_OBJECT (playbin, "can't switch video, we have no channels");
    return FALSE;
  }
}

static gboolean
gst_play_bin3_set_current_video_stream (GstPlayBin3 * playbin, gint stream)
{
  return gst_play_bin3_set_current_stream (playbin, PLAYBIN_STREAM_VIDEO,
      &playbin->current_video, stream, &playbin->video_pending_flush_finish);
}

static gboolean
gst_play_bin3_set_current_audio_stream (GstPlayBin3 * playbin, gint stream)
{
  return gst_play_bin3_set_current_stream (playbin, PLAYBIN_STREAM_AUDIO,
      &playbin->current_audio, stream, &playbin->audio_pending_flush_finish);
}

static gboolean
gst_play_bin3_set_current_text_stream (GstPlayBin3 * playbin, gint stream)
{
  return gst_play_bin3_set_current_stream (playbin, PLAYBIN_STREAM_TEXT,
      &playbin->current_text, stream, &playbin->text_pending_flush_finish);
}


static void
gst_play_bin3_set_sink (GstPlayBin3 * playbin, GstPlaySinkType type,
    const gchar * dbg, GstElement ** elem, GstElement * sink)
{
  GST_INFO_OBJECT (playbin, "Setting %s sink to %" GST_PTR_FORMAT, dbg, sink);

  gst_play_sink_set_sink (playbin->playsink, type, sink);

  if (*elem)
    gst_object_unref (*elem);
  *elem = sink ? gst_object_ref (sink) : NULL;
}

static void
gst_play_bin3_set_stream_combiner (GstPlayBin3 * playbin, GstElement ** elem,
    const gchar * dbg, GstElement * combiner)
{
  GST_INFO_OBJECT (playbin, "Setting %s stream combiner to %" GST_PTR_FORMAT,
      dbg, combiner);

  GST_PLAY_BIN3_LOCK (playbin);
  if (*elem != combiner) {
    GstElement *old;

    old = *elem;
    if (combiner)
      gst_object_ref_sink (combiner);

    *elem = combiner;
    if (old)
      gst_object_unref (old);
  }
  GST_LOG_OBJECT (playbin, "%s stream combiner now %" GST_PTR_FORMAT, dbg,
      *elem);
  GST_PLAY_BIN3_UNLOCK (playbin);
}

static void
gst_play_bin3_set_encoding (GstPlayBin3 * playbin, const gchar * encoding)
{
  GST_PLAY_BIN3_LOCK (playbin);
  gst_play_sink_set_subtitle_encoding (playbin->playsink, encoding);
  GST_PLAY_BIN3_UNLOCK (playbin);
}

static void
gst_play_bin3_set_property (GObject * object, guint prop_id,
    const GValue * value, GParamSpec * pspec)
{
  GstPlayBin3 *playbin = GST_PLAY_BIN3 (object);

  switch (prop_id) {
    case PROP_URI:
      gst_play_bin3_set_uri (playbin, g_value_get_string (value));
      break;
    case PROP_SUBURI:
      gst_play_bin3_set_suburi (playbin, g_value_get_string (value));
      break;
    case PROP_FLAGS:
      gst_play_bin3_set_flags (playbin, g_value_get_flags (value));
      if (playbin->curr_group) {
        GST_SOURCE_GROUP_LOCK (playbin->curr_group);
        if (playbin->curr_group->uridecodebin) {
          g_object_set (playbin->curr_group->uridecodebin, "download",
              (g_value_get_flags (value) & GST_PLAY_FLAG_DOWNLOAD) != 0, NULL);
        }
        GST_SOURCE_GROUP_UNLOCK (playbin->curr_group);
      }
      break;
    case PROP_SUBTITLE_ENCODING:
      gst_play_bin3_set_encoding (playbin, g_value_get_string (value));
      break;
    case PROP_VIDEO_FILTER:
      gst_play_sink_set_filter (playbin->playsink, GST_PLAY_SINK_TYPE_VIDEO,
          GST_ELEMENT (g_value_get_object (value)));
      break;
    case PROP_AUDIO_FILTER:
      gst_play_sink_set_filter (playbin->playsink, GST_PLAY_SINK_TYPE_AUDIO,
          GST_ELEMENT (g_value_get_object (value)));
      break;
    case PROP_VIDEO_SINK:
      gst_play_bin3_set_sink (playbin, GST_PLAY_SINK_TYPE_VIDEO, "video",
          &playbin->video_sink, g_value_get_object (value));
      break;
    case PROP_AUDIO_SINK:
      gst_play_bin3_set_sink (playbin, GST_PLAY_SINK_TYPE_AUDIO, "audio",
          &playbin->audio_sink, g_value_get_object (value));
      break;
    case PROP_VIS_PLUGIN:
      gst_play_sink_set_vis_plugin (playbin->playsink,
          g_value_get_object (value));
      break;
    case PROP_TEXT_SINK:
      gst_play_bin3_set_sink (playbin, GST_PLAY_SINK_TYPE_TEXT, "text",
          &playbin->text_sink, g_value_get_object (value));
      break;
    case PROP_VIDEO_STREAM_COMBINER:
      gst_play_bin3_set_stream_combiner (playbin,
          &playbin->video_stream_combiner, "video", g_value_get_object (value));
      break;
    case PROP_AUDIO_STREAM_COMBINER:
      gst_play_bin3_set_stream_combiner (playbin,
          &playbin->audio_stream_combiner, "audio", g_value_get_object (value));
      break;
    case PROP_TEXT_STREAM_COMBINER:
      gst_play_bin3_set_stream_combiner (playbin,
          &playbin->text_stream_combiner, "text", g_value_get_object (value));
      break;
    case PROP_VOLUME:
      gst_play_sink_set_volume (playbin->playsink, g_value_get_double (value));
      break;
    case PROP_MUTE:
      gst_play_sink_set_mute (playbin->playsink, g_value_get_boolean (value));
      break;
    case PROP_FONT_DESC:
      gst_play_sink_set_font_desc (playbin->playsink,
          g_value_get_string (value));
      break;
    case PROP_CONNECTION_SPEED:
      GST_PLAY_BIN3_LOCK (playbin);
      playbin->connection_speed = g_value_get_uint64 (value) * 1000;
      GST_PLAY_BIN3_UNLOCK (playbin);
      break;
    case PROP_BUFFER_SIZE:
      playbin->buffer_size = g_value_get_int (value);
      break;
    case PROP_BUFFER_DURATION:
      playbin->buffer_duration = g_value_get_int64 (value);
      break;
    case PROP_AV_OFFSET:
      gst_play_sink_set_av_offset (playbin->playsink,
          g_value_get_int64 (value));
      break;
    case PROP_RING_BUFFER_MAX_SIZE:
      playbin->ring_buffer_max_size = g_value_get_uint64 (value);
      if (playbin->curr_group) {
        GST_SOURCE_GROUP_LOCK (playbin->curr_group);
        if (playbin->curr_group->uridecodebin) {
          g_object_set (playbin->curr_group->uridecodebin,
              "ring-buffer-max-size", playbin->ring_buffer_max_size, NULL);
        }
        GST_SOURCE_GROUP_UNLOCK (playbin->curr_group);
      }
      break;
    case PROP_FORCE_ASPECT_RATIO:
      g_object_set (playbin->playsink, "force-aspect-ratio",
          g_value_get_boolean (value), NULL);
      break;
    case PROP_MULTIVIEW_MODE:
      GST_PLAY_BIN3_LOCK (playbin);
      playbin->multiview_mode = g_value_get_enum (value);
      GST_PLAY_BIN3_UNLOCK (playbin);
      break;
    case PROP_MULTIVIEW_FLAGS:
      GST_PLAY_BIN3_LOCK (playbin);
      playbin->multiview_flags = g_value_get_flags (value);
      GST_PLAY_BIN3_UNLOCK (playbin);
      break;
    default:
      G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
      break;
  }
}

static GstElement *
gst_play_bin3_get_current_sink (GstPlayBin3 * playbin, GstElement ** elem,
    const gchar * dbg, GstPlaySinkType type)
{
  GstElement *sink = gst_play_sink_get_sink (playbin->playsink, type);

  GST_LOG_OBJECT (playbin, "play_sink_get_sink() returned %s sink %"
      GST_PTR_FORMAT ", the originally set %s sink is %" GST_PTR_FORMAT,
      dbg, sink, dbg, *elem);

  if (sink == NULL) {
    GST_PLAY_BIN3_LOCK (playbin);
    if ((sink = *elem))
      gst_object_ref (sink);
    GST_PLAY_BIN3_UNLOCK (playbin);
  }

  return sink;
}

static GstElement *
gst_play_bin3_get_current_stream_combiner (GstPlayBin3 * playbin,
    GstElement ** elem, const gchar * dbg, int stream_type)
{
  GstElement *combiner;

  GST_PLAY_BIN3_LOCK (playbin);
  /* The special concat element should never be returned */
  if (playbin->combiner[stream_type].is_concat)
    combiner = NULL;
  else if ((combiner = playbin->combiner[stream_type].combiner))
    gst_object_ref (combiner);
  else if ((combiner = *elem))
    gst_object_ref (combiner);
  GST_PLAY_BIN3_UNLOCK (playbin);

  return combiner;
}

static void
gst_play_bin3_get_property (GObject * object, guint prop_id, GValue * value,
    GParamSpec * pspec)
{
  GstPlayBin3 *playbin = GST_PLAY_BIN3 (object);

  switch (prop_id) {
    case PROP_URI:
    {
      GstSourceGroup *group;

      GST_PLAY_BIN3_LOCK (playbin);
      group = playbin->next_group;
      g_value_set_string (value, group->uri);
      GST_PLAY_BIN3_UNLOCK (playbin);
      break;
    }
    case PROP_CURRENT_URI:
    {
      GstSourceGroup *group;

      GST_PLAY_BIN3_LOCK (playbin);
      group = get_group (playbin);
      g_value_set_string (value, group->uri);
      GST_PLAY_BIN3_UNLOCK (playbin);
      break;
    }
    case PROP_SUBURI:
    {
      GstSourceGroup *group;

      GST_PLAY_BIN3_LOCK (playbin);
      group = playbin->next_group;
      g_value_set_string (value, group->suburi);
      GST_PLAY_BIN3_UNLOCK (playbin);
      break;
    }
    case PROP_CURRENT_SUBURI:
    {
      GstSourceGroup *group;

      GST_PLAY_BIN3_LOCK (playbin);
      group = get_group (playbin);
      g_value_set_string (value, group->suburi);
      GST_PLAY_BIN3_UNLOCK (playbin);
      break;
    }
    case PROP_FLAGS:
      g_value_set_flags (value, gst_play_bin3_get_flags (playbin));
      break;
    case PROP_SUBTITLE_ENCODING:
      GST_PLAY_BIN3_LOCK (playbin);
      g_value_take_string (value,
          gst_play_sink_get_subtitle_encoding (playbin->playsink));
      GST_PLAY_BIN3_UNLOCK (playbin);
      break;
    case PROP_VIDEO_FILTER:
      g_value_take_object (value,
          gst_play_sink_get_filter (playbin->playsink,
              GST_PLAY_SINK_TYPE_VIDEO));
      break;
    case PROP_AUDIO_FILTER:
      g_value_take_object (value,
          gst_play_sink_get_filter (playbin->playsink,
              GST_PLAY_SINK_TYPE_AUDIO));
      break;
    case PROP_VIDEO_SINK:
      g_value_take_object (value,
          gst_play_bin3_get_current_sink (playbin, &playbin->video_sink,
              "video", GST_PLAY_SINK_TYPE_VIDEO));
      break;
    case PROP_AUDIO_SINK:
      g_value_take_object (value,
          gst_play_bin3_get_current_sink (playbin, &playbin->audio_sink,
              "audio", GST_PLAY_SINK_TYPE_AUDIO));
      break;
    case PROP_VIS_PLUGIN:
      g_value_take_object (value,
          gst_play_sink_get_vis_plugin (playbin->playsink));
      break;
    case PROP_TEXT_SINK:
      g_value_take_object (value,
          gst_play_bin3_get_current_sink (playbin, &playbin->text_sink,
              "text", GST_PLAY_SINK_TYPE_TEXT));
      break;
    case PROP_VIDEO_STREAM_COMBINER:
      g_value_take_object (value,
          gst_play_bin3_get_current_stream_combiner (playbin,
              &playbin->video_stream_combiner, "video", PLAYBIN_STREAM_VIDEO));
      break;
    case PROP_AUDIO_STREAM_COMBINER:
      g_value_take_object (value,
          gst_play_bin3_get_current_stream_combiner (playbin,
              &playbin->audio_stream_combiner, "audio", PLAYBIN_STREAM_AUDIO));
      break;
    case PROP_TEXT_STREAM_COMBINER:
      g_value_take_object (value,
          gst_play_bin3_get_current_stream_combiner (playbin,
              &playbin->text_stream_combiner, "text", PLAYBIN_STREAM_TEXT));
      break;
    case PROP_VOLUME:
      g_value_set_double (value, gst_play_sink_get_volume (playbin->playsink));
      break;
    case PROP_MUTE:
      g_value_set_boolean (value, gst_play_sink_get_mute (playbin->playsink));
      break;
    case PROP_SAMPLE:
      gst_value_take_sample (value,
          gst_play_sink_get_last_sample (playbin->playsink));
      break;
    case PROP_FONT_DESC:
      g_value_take_string (value,
          gst_play_sink_get_font_desc (playbin->playsink));
      break;
    case PROP_CONNECTION_SPEED:
      GST_PLAY_BIN3_LOCK (playbin);
      g_value_set_uint64 (value, playbin->connection_speed / 1000);
      GST_PLAY_BIN3_UNLOCK (playbin);
      break;
    case PROP_BUFFER_SIZE:
      GST_OBJECT_LOCK (playbin);
      g_value_set_int (value, playbin->buffer_size);
      GST_OBJECT_UNLOCK (playbin);
      break;
    case PROP_BUFFER_DURATION:
      GST_OBJECT_LOCK (playbin);
      g_value_set_int64 (value, playbin->buffer_duration);
      GST_OBJECT_UNLOCK (playbin);
      break;
    case PROP_AV_OFFSET:
      g_value_set_int64 (value,
          gst_play_sink_get_av_offset (playbin->playsink));
      break;
    case PROP_RING_BUFFER_MAX_SIZE:
      g_value_set_uint64 (value, playbin->ring_buffer_max_size);
      break;
    case PROP_FORCE_ASPECT_RATIO:{
      gboolean v;

      g_object_get (playbin->playsink, "force-aspect-ratio", &v, NULL);
      g_value_set_boolean (value, v);
      break;
    }
    case PROP_MULTIVIEW_MODE:
      GST_OBJECT_LOCK (playbin);
      g_value_set_enum (value, playbin->multiview_mode);
      GST_OBJECT_UNLOCK (playbin);
      break;
    case PROP_MULTIVIEW_FLAGS:
      GST_OBJECT_LOCK (playbin);
      g_value_set_flags (value, playbin->multiview_flags);
      GST_OBJECT_UNLOCK (playbin);
      break;
    default:
      G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
      break;
  }
}

static gint
get_combiner_stream_id (GstPlayBin3 * playbin, GstSourceCombine * combine,
    GList * full_list)
{
  gint i;
  GList *tmp;

  for (i = 0; i < combine->streams->len; i++) {
    GstStream *stream = (GstStream *) g_ptr_array_index (combine->streams, i);
    const gchar *sid = gst_stream_get_stream_id (stream);
    for (tmp = full_list; tmp; tmp = tmp->next) {
      gchar *orig = (gchar *) tmp->data;
      if (!g_strcmp0 (orig, sid))
        return i;
    }
  }

  /* Fallback */
  return -1;
}

static GList *
extend_list_of_streams (GstPlayBin3 * playbin, GstStreamType stype,
    GList * list, GstStreamCollection * collection)
{
  GList *tmp, *res;
  gint i, nb;

  res = list;

  nb = gst_stream_collection_get_size (collection);
  for (i = 0; i < nb; i++) {
    GstStream *stream = gst_stream_collection_get_stream (collection, i);
    GstStreamType curtype = gst_stream_get_stream_type (stream);
    if (stype == curtype) {
      gboolean already_there = FALSE;
      const gchar *sid = gst_stream_get_stream_id (stream);
      for (tmp = res; tmp; tmp = tmp->next) {
        const gchar *other = (const gchar *) tmp->data;
        if (!g_strcmp0 (sid, other)) {
          already_there = TRUE;
          break;
        }
      }
      if (!already_there) {
        GST_DEBUG_OBJECT (playbin, "Adding stream %s", sid);
        res = g_list_append (res, g_strdup (sid));
      }
    }
  }

  return res;
}

static GstEvent *
update_select_streams_event (GstPlayBin3 * playbin, GstEvent * event,
    GstSourceGroup * group)
{
  GList *streams = NULL;
  GList *to_use;
  gint combine_id;

  if (!playbin->audio_stream_combiner && !playbin->video_stream_combiner &&
      !playbin->text_stream_combiner) {
    /* Nothing to do */
    GST_DEBUG_OBJECT (playbin,
        "No custom combiners, no need to modify SELECT_STREAMS event");
    return event;
  }

  if (!group->collection) {
    GST_DEBUG_OBJECT (playbin,
        "No stream collection for group, no need to modify SELECT_STREAMS event");
    return event;
  }

  gst_event_parse_select_streams (event, &streams);
  to_use = g_list_copy_deep (streams, (GCopyFunc) g_strdup, NULL);

  /* For each combiner, we want to add all streams of that type to the
   * selection */
  if (playbin->audio_stream_combiner) {
    to_use =
        extend_list_of_streams (playbin, GST_STREAM_TYPE_AUDIO, to_use,
        group->collection);
    combine_id =
        get_combiner_stream_id (playbin,
        &playbin->combiner[PLAYBIN_STREAM_AUDIO], streams);
    if (combine_id != -1)
      gst_play_bin3_set_current_audio_stream (playbin, combine_id);
  }
  if (playbin->video_stream_combiner) {
    to_use =
        extend_list_of_streams (playbin, GST_STREAM_TYPE_VIDEO, to_use,
        group->collection);
    combine_id =
        get_combiner_stream_id (playbin,
        &playbin->combiner[PLAYBIN_STREAM_VIDEO], streams);
    if (combine_id != -1)
      gst_play_bin3_set_current_video_stream (playbin, combine_id);
  }
  if (playbin->text_stream_combiner) {
    to_use =
        extend_list_of_streams (playbin, GST_STREAM_TYPE_TEXT, to_use,
        group->collection);
    combine_id =
        get_combiner_stream_id (playbin,
        &playbin->combiner[PLAYBIN_STREAM_TEXT], streams);
    if (combine_id != -1)
      gst_play_bin3_set_current_text_stream (playbin, combine_id);
  }

  gst_event_unref (event);
  event = gst_event_new_select_streams (to_use);

  if (streams)
    g_list_free_full (streams, g_free);
  if (to_use)
    g_list_free_full (to_use, g_free);

  return event;
}

/* Returns TRUE if the given list of streams belongs to the stream collection */
static gboolean
gst_streams_belong_to_collection (GList * streams,
    GstStreamCollection * collection)
{
  GList *tmp;
  guint i, nb;

  if (streams == NULL || collection == NULL)
    return FALSE;
  nb = gst_stream_collection_get_size (collection);
  if (nb == 0)
    return FALSE;

  for (tmp = streams; tmp; tmp = tmp->next) {
    const gchar *cand = (const gchar *) tmp->data;
    gboolean found = FALSE;

    for (i = 0; i < nb; i++) {
      GstStream *stream = gst_stream_collection_get_stream (collection, i);
      if (!g_strcmp0 (cand, gst_stream_get_stream_id (stream))) {
        found = TRUE;
        break;
      }
    }
    if (!found)
      return FALSE;
  }
  return TRUE;
}

static GstSourceGroup *
get_source_group_for_streams (GstPlayBin3 * playbin, GstEvent * event)
{
  GList *streams;
  GstSourceGroup *res = NULL;

  gst_event_parse_select_streams (event, &streams);
  if (playbin->curr_group->collection &&
      gst_streams_belong_to_collection (streams,
          playbin->curr_group->collection))
    res = playbin->curr_group;
  else if (playbin->next_group->collection &&
      gst_streams_belong_to_collection (streams,
          playbin->next_group->collection))
    res = playbin->next_group;
  g_list_free_full (streams, g_free);

  return res;
}

static GstStreamType
get_stream_type_for_event (GstStreamCollection * collection, GstEvent * event)
{
  GList *stream_list = NULL;
  GList *tmp;
  GstStreamType res = 0;
  guint i, len;

  gst_event_parse_select_streams (event, &stream_list);
  len = gst_stream_collection_get_size (collection);
  for (tmp = stream_list; tmp; tmp = tmp->next) {
    gchar *stid = (gchar *) tmp->data;

    for (i = 0; i < len; i++) {
      GstStream *stream = gst_stream_collection_get_stream (collection, i);
      if (!g_strcmp0 (stid, gst_stream_get_stream_id (stream))) {
        res |= gst_stream_get_stream_type (stream);
      }
    }
  }
  g_list_free_full (stream_list, g_free);

  return res;
}

static gboolean
gst_play_bin3_send_event (GstElement * element, GstEvent * event)
{
  GstPlayBin3 *playbin = GST_PLAY_BIN3 (element);

  if (GST_EVENT_TYPE (event) == GST_EVENT_SELECT_STREAMS) {
    gboolean res;
    GstSourceGroup *group;

    GST_PLAY_BIN3_LOCK (playbin);
    GST_LOG_OBJECT (playbin,
        "App sent select-streams, we won't do anything ourselves now");
    /* This is probably already false, but it doesn't hurt to be sure */
    playbin->do_stream_selections = FALSE;

    group = get_source_group_for_streams (playbin, event);
    if (group == NULL) {
      GST_WARNING_OBJECT (playbin,
          "Can't figure out to which uridecodebin the select-streams event should be sent to");
      GST_PLAY_BIN3_UNLOCK (playbin);
      return FALSE;
    }

    /* If we have custom combiners, we need to extend the selection with
     * the list of all streams for that given type since we will be handling
     * the selection with that combiner */
    event = update_select_streams_event (playbin, event, group);

    if (group->collection) {
      group->selected_stream_types =
          get_stream_type_for_event (group->collection, event);
      playbin->selected_stream_types =
          playbin->groups[0].selected_stream_types | playbin->
          groups[1].selected_stream_types;
      if (playbin->active_stream_types != playbin->selected_stream_types)
        reconfigure_output (playbin);
    }

    /* Send this event directly to uridecodebin, so it works even
     * if uridecodebin didn't add any pads yet */
    res = gst_element_send_event (group->uridecodebin, event);
    GST_PLAY_BIN3_UNLOCK (playbin);

    return res;
  }

  /* Send event directly to playsink instead of letting GstBin iterate
   * over all sink elements. The latter might send the event multiple times
   * in case the SEEK causes a reconfiguration of the pipeline, as can easily
   * happen with adaptive streaming demuxers.
   *
   * What would then happen is that the iterator would be reset, we send the
   * event again, and on the second time it will fail in the majority of cases
   * because the pipeline is still being reconfigured
   */
  if (GST_EVENT_IS_UPSTREAM (event)) {
    return gst_element_send_event (GST_ELEMENT_CAST (playbin->playsink), event);
  }

  return GST_ELEMENT_CLASS (parent_class)->send_event (element, event);
}

/* Called with playbin lock held */
static void
do_stream_selection (GstPlayBin3 * playbin, GstSourceGroup * group)
{
  GstStreamCollection *collection;
  guint i, nb_streams;
  GList *streams = NULL;
  gint nb_video = 0, nb_audio = 0, nb_text = 0;
  GstStreamType chosen_stream_types = 0;

  if (group == NULL)
    return;

  collection = group->collection;
  if (collection == NULL) {
    GST_LOG_OBJECT (playbin, "No stream collection. Not doing stream-select");
    return;
  }

  nb_streams = gst_stream_collection_get_size (collection);
  if (nb_streams == 0) {
    GST_INFO_OBJECT (playbin, "Empty collection received! Ignoring");
  }

  GST_DEBUG_OBJECT (playbin, "Doing selection on collection with %d streams",
      nb_streams);

  /* Iterate the collection and choose the streams that match
   * either the current-* setting, or all streams of a type if there's
   * a combiner for that type */
  for (i = 0; i < nb_streams; i++) {
    GstStream *stream = gst_stream_collection_get_stream (collection, i);
    GstStreamType stream_type = gst_stream_get_stream_type (stream);
    const gchar *stream_id = gst_stream_get_stream_id (stream);
    gint pb_stream_type = -1;
    gboolean select_this = FALSE;

    GST_LOG_OBJECT (playbin, "Looking at stream #%d : %s", i, stream_id);

    if (stream_type & GST_STREAM_TYPE_AUDIO) {
      pb_stream_type = PLAYBIN_STREAM_AUDIO;
      /* Select the stream if it's the current one or if there's a custom selector */
      select_this =
          (nb_audio == playbin->current_audio ||
          (playbin->current_audio == -1 && nb_audio == 0) ||
          playbin->audio_stream_combiner != NULL);
      nb_audio++;
    } else if (stream_type & GST_STREAM_TYPE_VIDEO) {
      pb_stream_type = PLAYBIN_STREAM_VIDEO;
      select_this =
          (nb_video == playbin->current_video ||
          (playbin->current_video == -1 && nb_video == 0) ||
          playbin->video_stream_combiner != NULL);
      nb_video++;
    } else if (stream_type & GST_STREAM_TYPE_TEXT) {
      pb_stream_type = PLAYBIN_STREAM_TEXT;
      select_this =
          (nb_text == playbin->current_text ||
          (playbin->current_text == -1 && nb_text == 0) ||
          playbin->text_stream_combiner != NULL);
      nb_text++;
    }
    if (pb_stream_type < 0) {
      GST_DEBUG_OBJECT (playbin,
          "Stream %d (id %s) of unhandled type %s. Ignoring", i, stream_id,
          gst_stream_type_get_name (stream_type));
      continue;
    }
    if (select_this) {
      GST_DEBUG_OBJECT (playbin, "Selecting stream %s of type %s",
          stream_id, gst_stream_type_get_name (stream_type));
      /* Don't build the list if we're not in charge of stream selection */
      if (playbin->do_stream_selections)
        streams = g_list_append (streams, (gpointer) stream_id);
      chosen_stream_types |= stream_type;
    }
  }

  if (streams) {
    if (group->uridecodebin) {
      GstEvent *ev = gst_event_new_select_streams (streams);
      gst_element_send_event (group->uridecodebin, ev);
    }
    g_list_free (streams);
  }

  group->selected_stream_types = chosen_stream_types;
  /* Update global selected_stream_types */
  playbin->selected_stream_types =
      playbin->groups[0].selected_stream_types | playbin->
      groups[1].selected_stream_types;
  if (playbin->active_stream_types != playbin->selected_stream_types)
    reconfigure_output (playbin);
}

/* Return the GstSourceGroup to which this element belongs
 * Can be NULL (if it belongs to playsink for example) */
static GstSourceGroup *
find_source_group_owner (GstPlayBin3 * playbin, GstObject * element)
{
  if (playbin->curr_group->uridecodebin
      && gst_object_has_as_ancestor (element,
          GST_OBJECT_CAST (playbin->curr_group->uridecodebin)))
    return playbin->curr_group;
  if (playbin->next_group->uridecodebin
      && gst_object_has_as_ancestor (element,
          GST_OBJECT_CAST (playbin->next_group->uridecodebin)))
    return playbin->next_group;
  return NULL;
}

static void
gst_play_bin3_handle_message (GstBin * bin, GstMessage * msg)
{
  GstPlayBin3 *playbin = GST_PLAY_BIN3 (bin);

  if (GST_MESSAGE_TYPE (msg) == GST_MESSAGE_STREAM_START) {
    GstSourceGroup *group = NULL, *other_group = NULL;
    gboolean changed = FALSE;
    guint group_id;
    GstMessage *buffering_msg;

    if (!gst_message_parse_group_id (msg, &group_id)) {
      GST_ERROR_OBJECT (bin,
          "Could not get group_id from STREAM_START message !");
      goto beach;
    }
    GST_DEBUG_OBJECT (bin, "STREAM_START group_id:%u", group_id);

    /* Figure out to which group this group_id corresponds */
    GST_PLAY_BIN3_LOCK (playbin);
    if (playbin->groups[0].group_id == group_id) {
      group = &playbin->groups[0];
      other_group = &playbin->groups[1];
    } else if (playbin->groups[1].group_id == group_id) {
      group = &playbin->groups[1];
      other_group = &playbin->groups[0];
    }
    if (group == NULL) {
      GST_ERROR_OBJECT (bin, "group_id %u is not provided by any group !",
          group_id);
      GST_PLAY_BIN3_UNLOCK (playbin);
      goto beach;
    }

    debug_groups (playbin);

    /* Do the switch now ! */
    playbin->curr_group = group;
    playbin->next_group = other_group;

    GST_SOURCE_GROUP_LOCK (group);
    if (group->playing == FALSE)
      changed = TRUE;
    group->playing = TRUE;
    buffering_msg = group->pending_buffering_msg;
    group->pending_buffering_msg = NULL;
    GST_SOURCE_GROUP_UNLOCK (group);

    GST_SOURCE_GROUP_LOCK (other_group);
    other_group->playing = FALSE;
    GST_SOURCE_GROUP_UNLOCK (other_group);

    debug_groups (playbin);
    GST_PLAY_BIN3_UNLOCK (playbin);
    if (changed)
      gst_play_bin3_check_group_status (playbin);
    else
      GST_DEBUG_OBJECT (bin, "Groups didn't changed");
    /* If there was a pending buffering message to send, do it now */
    if (buffering_msg)
      GST_BIN_CLASS (parent_class)->handle_message (bin, buffering_msg);
  } else if (GST_MESSAGE_TYPE (msg) == GST_MESSAGE_BUFFERING) {
    GstSourceGroup *group;

    /* Only post buffering messages for group which is currently playing */
    group = find_source_group_owner (playbin, msg->src);
    GST_SOURCE_GROUP_LOCK (group);
    if (!group->playing) {
      GST_DEBUG_OBJECT (playbin, "Storing buffering message from pending group "
          "%p %" GST_PTR_FORMAT, group, msg);
      gst_message_replace (&group->pending_buffering_msg, msg);
      gst_message_unref (msg);
      msg = NULL;
    }
    GST_SOURCE_GROUP_UNLOCK (group);
  } else if (GST_MESSAGE_TYPE (msg) == GST_MESSAGE_STREAM_COLLECTION) {
    GstStreamCollection *collection = NULL;

    gst_message_parse_stream_collection (msg, &collection);

    if (collection) {
      gboolean pstate = playbin->do_stream_selections;
      GstSourceGroup *target_group = NULL;

      GST_PLAY_BIN3_LOCK (playbin);
      GST_DEBUG_OBJECT (playbin,
          "STREAM_COLLECTION: Got a collection from %" GST_PTR_FORMAT,
          msg->src);
      target_group = find_source_group_owner (playbin, msg->src);
      if (target_group)
        gst_object_replace ((GstObject **) & target_group->collection,
            (GstObject *) collection);
      /* FIXME: Only do the following if it's the current group? */
      if (target_group == playbin->curr_group)
        update_combiner_info (playbin, target_group->collection);
      if (pstate)
        playbin->do_stream_selections = FALSE;
      do_stream_selection (playbin, target_group);
      if (pstate)
        playbin->do_stream_selections = TRUE;
      GST_PLAY_BIN3_UNLOCK (playbin);

      gst_object_unref (collection);
    }
  }

beach:
  if (msg)
    GST_BIN_CLASS (parent_class)->handle_message (bin, msg);
}

static void
gst_play_bin3_deep_element_added (GstBin * playbin, GstBin * sub_bin,
    GstElement * child)
{
  GST_LOG_OBJECT (playbin, "element %" GST_PTR_FORMAT " was added to "
      "%" GST_PTR_FORMAT, child, sub_bin);

  g_signal_emit (playbin, gst_play_bin3_signals[SIGNAL_ELEMENT_SETUP], 0,
      child);

  GST_BIN_CLASS (parent_class)->deep_element_added (playbin, sub_bin, child);
}

/* Returns current stream number, or -1 if none has been selected yet */
static int
get_current_stream_number (GstPlayBin3 * playbin, GstSourceCombine * combine,
    GPtrArray * channels)
{
  /* Internal API cleanup would make this easier... */
  int i;
  GstPad *pad, *current;
  GstObject *combiner = NULL;
  int ret = -1;

  if (!combine->has_active_pad) {
    GST_WARNING_OBJECT (playbin,
        "combiner doesn't have the \"active-pad\" property");
    return ret;
  }

  for (i = 0; i < channels->len; i++) {
    pad = g_ptr_array_index (channels, i);
    if ((combiner = gst_pad_get_parent (pad))) {
      g_object_get (combiner, "active-pad", &current, NULL);
      gst_object_unref (combiner);

      if (pad == current) {
        gst_object_unref (current);
        ret = i;
        break;
      }

      if (current)
        gst_object_unref (current);
    }
  }

  return ret;
}

static void
combiner_active_pad_changed (GObject * combiner, GParamSpec * pspec,
    GstPlayBin3 * playbin)
{
  GstSourceCombine *combine = NULL;
  GPtrArray *channels = NULL;
  int i;

  GST_PLAY_BIN3_LOCK (playbin);

  for (i = 0; i < PLAYBIN_STREAM_LAST; i++) {
    if (combiner == G_OBJECT (playbin->combiner[i].combiner)) {
      combine = &playbin->combiner[i];
      channels = playbin->channels[i];
    }
  }

  /* We got a pad-change after our group got switched out; no need to notify */
  if (!combine) {
    GST_PLAY_BIN3_UNLOCK (playbin);
    return;
  }

  switch (combine->type) {
    case GST_PLAY_SINK_TYPE_VIDEO:
    case GST_PLAY_SINK_TYPE_VIDEO_RAW:
      playbin->current_video = get_current_stream_number (playbin,
          combine, channels);

      if (playbin->video_pending_flush_finish) {
        playbin->video_pending_flush_finish = FALSE;
        GST_PLAY_BIN3_UNLOCK (playbin);
        gst_play_bin3_send_custom_event (GST_OBJECT (combiner),
            "playsink-custom-video-flush-finish");
      }
      break;
    case GST_PLAY_SINK_TYPE_AUDIO:
    case GST_PLAY_SINK_TYPE_AUDIO_RAW:
      playbin->current_audio = get_current_stream_number (playbin,
          combine, channels);

      if (playbin->audio_pending_flush_finish) {
        playbin->audio_pending_flush_finish = FALSE;
        GST_PLAY_BIN3_UNLOCK (playbin);
        gst_play_bin3_send_custom_event (GST_OBJECT (combiner),
            "playsink-custom-audio-flush-finish");
      }
      break;
    case GST_PLAY_SINK_TYPE_TEXT:
      playbin->current_text = get_current_stream_number (playbin,
          combine, channels);

      if (playbin->text_pending_flush_finish) {
        playbin->text_pending_flush_finish = FALSE;
        GST_PLAY_BIN3_UNLOCK (playbin);
        gst_play_bin3_send_custom_event (GST_OBJECT (combiner),
            "playsink-custom-subtitle-flush-finish");
      }
      break;
    default:
      break;
  }
  GST_PLAY_BIN3_UNLOCK (playbin);
}

static GstCaps *
update_video_multiview_caps (GstPlayBin3 * playbin, GstCaps * caps)
{
  GstVideoMultiviewMode mv_mode;
  GstVideoMultiviewMode cur_mv_mode;
  guint mv_flags, cur_mv_flags;
  GstStructure *s;
  const gchar *mview_mode_str;
  GstCaps *out_caps;

  GST_OBJECT_LOCK (playbin);
  mv_mode = (GstVideoMultiviewMode) playbin->multiview_mode;
  mv_flags = playbin->multiview_flags;
  GST_OBJECT_UNLOCK (playbin);

  if (mv_mode == GST_VIDEO_MULTIVIEW_MODE_NONE)
    return NULL;

  cur_mv_mode = GST_VIDEO_MULTIVIEW_MODE_NONE;
  cur_mv_flags = GST_VIDEO_MULTIVIEW_FLAGS_NONE;

  s = gst_caps_get_structure (caps, 0);

  gst_structure_get_flagset (s, "multiview-flags", &cur_mv_flags, NULL);
  if ((mview_mode_str = gst_structure_get_string (s, "multiview-mode")))
    cur_mv_mode = gst_video_multiview_mode_from_caps_string (mview_mode_str);

  /* We can't override an existing annotated multiview mode, except
   * maybe (in the future) we could change some flags. */
  if ((gint) cur_mv_mode > GST_VIDEO_MULTIVIEW_MAX_FRAME_PACKING) {
    GST_INFO_OBJECT (playbin, "Cannot override existing multiview mode");
    return NULL;
  }

  mview_mode_str = gst_video_multiview_mode_to_caps_string (mv_mode);
  g_assert (mview_mode_str != NULL);
  out_caps = gst_caps_copy (caps);
  s = gst_caps_get_structure (out_caps, 0);

  gst_structure_set (s, "multiview-mode", G_TYPE_STRING, mview_mode_str,
      "multiview-flags", GST_TYPE_VIDEO_MULTIVIEW_FLAGSET, mv_flags,
      GST_FLAG_SET_MASK_EXACT, NULL);

  return out_caps;
}

static void
emit_about_to_finish (GstPlayBin3 * playbin)
{
  GST_DEBUG_OBJECT (playbin, "Emitting about-to-finish");

  /* after this call, we should have a next group to activate or we EOS */
  g_signal_emit (G_OBJECT (playbin),
      gst_play_bin3_signals[SIGNAL_ABOUT_TO_FINISH], 0, NULL);

  debug_groups (playbin);

  /* now activate the next group. If the app did not set a uri, this will
   * fail and we can do EOS */
  setup_next_source (playbin);
}

static SourcePad *
find_source_pad (GstSourceGroup * group, GstPad * target)
{
  GList *tmp;

  for (tmp = group->source_pads; tmp; tmp = tmp->next) {
    SourcePad *res = (SourcePad *) tmp->data;
    if (res->pad == target)
      return res;
  }
  return NULL;
}

static GstPadProbeReturn
_decodebin_event_probe (GstPad * pad, GstPadProbeInfo * info, gpointer udata)
{
  GstPadProbeReturn ret = GST_PAD_PROBE_OK;
  GstSourceGroup *group = (GstSourceGroup *) udata;
  GstPlayBin3 *playbin = group->playbin;
  GstEvent *event = GST_PAD_PROBE_INFO_DATA (info);

  switch (GST_EVENT_TYPE (event)) {
    case GST_EVENT_CAPS:{
      GstCaps *caps = NULL;
      const GstStructure *s;
      const gchar *name;

      gst_event_parse_caps (event, &caps);
      /* If video caps, check if we should override multiview flags */
      s = gst_caps_get_structure (caps, 0);
      name = gst_structure_get_name (s);
      if (g_str_has_prefix (name, "video/")) {
        caps = update_video_multiview_caps (playbin, caps);
        if (caps) {
          gst_event_unref (event);
          event = gst_event_new_caps (caps);
          GST_PAD_PROBE_INFO_DATA (info) = event;
          gst_caps_unref (caps);
        }
      }
      break;
    }
    case GST_EVENT_STREAM_START:
    {
      guint group_id;
      if (gst_event_parse_group_id (event, &group_id)) {
        GST_LOG_OBJECT (pad, "STREAM_START group_id:%u", group_id);
        if (group->group_id == GST_GROUP_ID_INVALID)
          group->group_id = group_id;
        else if (group->group_id != group_id) {
          GST_DEBUG_OBJECT (pad, "group_id changing from %u to %u",
              group->group_id, group_id);
          group->group_id = group_id;
        }
      }
      break;
    }
    default:
      break;
  }

  return ret;
}

static void
control_source_pad (GstSourceGroup * group, GstPad * pad,
    GstStreamType stream_type)
{
  SourcePad *sourcepad = g_slice_new0 (SourcePad);

  sourcepad->pad = pad;
  sourcepad->event_probe_id =
      gst_pad_add_probe (pad, GST_PAD_PROBE_TYPE_EVENT_DOWNSTREAM,
      _decodebin_event_probe, group, NULL);
  sourcepad->stream_type = stream_type;
  group->source_pads = g_list_append (group->source_pads, sourcepad);
}

static void
remove_combiner (GstPlayBin3 * playbin, GstSourceCombine * combine)
{
  gint n;

  if (combine->combiner == NULL) {
    GST_DEBUG_OBJECT (playbin, "No combiner element to remove");
    return;
  }

  /* Go over all sink pads and release them ! */
  for (n = 0; n < combine->channels->len; n++) {
    GstPad *sinkpad = g_ptr_array_index (combine->channels, n);

    gst_element_release_request_pad (combine->combiner, sinkpad);
    gst_object_unref (sinkpad);
  }
  g_ptr_array_set_size (combine->channels, 0);

  gst_element_set_state (combine->combiner, GST_STATE_NULL);
  gst_bin_remove (GST_BIN_CAST (playbin), combine->combiner);
  combine->combiner = NULL;

}

/* Create the combiner element if needed for the given combine */
static void
create_combiner (GstPlayBin3 * playbin, GstSourceCombine * combine)
{
  GstElement *custom_combiner = NULL;

  if (combine->combiner) {
    GST_WARNING_OBJECT (playbin, "Combiner element already exists!");
    return;
  }

  if (combine->stream_type == GST_STREAM_TYPE_VIDEO)
    custom_combiner = playbin->video_stream_combiner;
  else if (combine->stream_type == GST_STREAM_TYPE_AUDIO)
    custom_combiner = playbin->audio_stream_combiner;
  else if (combine->stream_type == GST_STREAM_TYPE_TEXT)
    custom_combiner = playbin->text_stream_combiner;

  combine->combiner = custom_combiner;

  if (!combine->combiner) {
    gchar *concat_name;
    GST_DEBUG_OBJECT (playbin,
        "No custom combiner requested, using 'concat' element");
    concat_name = g_strdup_printf ("%s-concat", combine->media_type);
    combine->combiner = gst_element_factory_make ("concat", concat_name);
    g_object_set (combine->combiner, "adjust-base", FALSE, NULL);
    g_free (concat_name);
    combine->is_concat = TRUE;
  }

  combine->srcpad = gst_element_get_static_pad (combine->combiner, "src");

  /* We only want to use 'active-pad' if it's a regular combiner that
   * will consume all streams, and not concat (which is just used for
   * gapless) */
  if (!combine->is_concat) {
    combine->has_active_pad =
        g_object_class_find_property (G_OBJECT_GET_CLASS (combine->combiner),
        "active-pad") != NULL;

    if (combine->has_active_pad)
      g_signal_connect (combine->combiner, "notify::active-pad",
          G_CALLBACK (combiner_active_pad_changed), playbin);
  }

  GST_DEBUG_OBJECT (playbin, "adding new stream combiner %" GST_PTR_FORMAT,
      combine->combiner);
  gst_bin_add (GST_BIN_CAST (playbin), combine->combiner);
  gst_element_sync_state_with_parent (combine->combiner);
}

static gboolean
combiner_control_pad (GstPlayBin3 * playbin, GstSourceCombine * combine,
    GstPad * srcpad)
{
  GstPadLinkReturn res;

  GST_DEBUG_OBJECT (playbin, "srcpad %" GST_PTR_FORMAT, srcpad);

  if (combine->combiner) {
    GstPad *sinkpad =
        gst_element_get_request_pad (combine->combiner, "sink_%u");

    if (sinkpad == NULL)
      goto request_pad_failed;

    GST_DEBUG_OBJECT (playbin, "Got new combiner pad %" GST_PTR_FORMAT,
        sinkpad);

    /* store the pad in the array */
    GST_DEBUG_OBJECT (playbin, "pad %" GST_PTR_FORMAT " added to array",
        sinkpad);
    g_ptr_array_add (combine->channels, sinkpad);

    res = gst_pad_link (srcpad, sinkpad);
    if (GST_PAD_LINK_FAILED (res))
      goto failed_combiner_link;

    GST_DEBUG_OBJECT (playbin,
        "linked pad %" GST_PTR_FORMAT " to combiner %" GST_PTR_FORMAT, srcpad,
        combine->combiner);

  } else {
    GST_LOG_OBJECT (playbin, "combine->sinkpad:%" GST_PTR_FORMAT,
        combine->sinkpad);
    g_assert (combine->sinkpad != NULL);
    /* Connect directly to playsink */
    if (gst_pad_is_linked (combine->sinkpad))
      goto sinkpad_already_linked;

    GST_DEBUG_OBJECT (playbin, "Linking new pad straight to playsink");
    res = gst_pad_link (srcpad, combine->sinkpad);

    if (res != GST_PAD_LINK_OK)
      goto failed_sinkpad_link;
  }

  return TRUE;

  /* Failure cases */
request_pad_failed:
  GST_ELEMENT_ERROR (playbin, CORE, PAD,
      ("Internal playbin error."),
      ("Failed to get request pad from combiner %p.", combine->combiner));
  return FALSE;


sinkpad_already_linked:
  GST_ELEMENT_ERROR (playbin, CORE, PAD,
      ("Internal playbin error."), ("playsink pad already used !"));
  return FALSE;

failed_sinkpad_link:
  GST_ELEMENT_ERROR (playbin, CORE, PAD,
      ("Internal playbin error."),
      ("Failed to link pad to sink. Error %d", res));
  return FALSE;

failed_combiner_link:
  GST_ELEMENT_ERROR (playbin, CORE, PAD,
      ("Internal playbin error."),
      ("Failed to link pad to combiner. Error %d", res));
  return FALSE;
}

static void
combiner_release_pad (GstPlayBin3 * playbin, GstSourceCombine * combine,
    GstPad * pad)
{
  if (combine->combiner) {
    GstPad *peer = gst_pad_get_peer (pad);

    if (peer) {
      GST_DEBUG_OBJECT (playbin, "Removing combiner pad %" GST_PTR_FORMAT,
          peer);
      g_ptr_array_remove (combine->channels, peer);

      gst_element_release_request_pad (combine->combiner, peer);
      gst_object_unref (peer);
    }
  } else {
    /* Release direct link if present */
    if (combine->sinkpad) {
      GST_DEBUG_OBJECT (playbin, "Unlinking pad from playsink sinkpad");
      gst_pad_unlink (pad, combine->sinkpad);
    }
  }
}

/* Call after pad was unlinked from (potential) combiner */
static void
release_source_pad (GstPlayBin3 * playbin, GstSourceGroup * group, GstPad * pad)
{
  SourcePad *sourcepad;
  GList *tmp;
  GstStreamType alltype = 0;

  sourcepad = find_source_pad (group, pad);
  if (!sourcepad) {
    GST_DEBUG_OBJECT (playbin, "Not a pad controlled by us ?");
    return;
  }

  if (sourcepad->event_probe_id) {
    gst_pad_remove_probe (pad, sourcepad->event_probe_id);
    sourcepad->event_probe_id = 0;
  }

  /* Remove from list of controlled pads and check again for EOS status */
  group->source_pads = g_list_remove (group->source_pads, sourcepad);
  g_slice_free (SourcePad, sourcepad);

  /* Update present stream types */
  for (tmp = group->source_pads; tmp; tmp = tmp->next) {
    SourcePad *cand = (SourcePad *) tmp->data;
    alltype |= cand->stream_type;
  }
  group->present_stream_types = alltype;
}

/* this function is called when a new pad is added to decodebin. We check the
 * type of the pad and add it to the combiner element
 */
static void
pad_added_cb (GstElement * uridecodebin, GstPad * pad, GstSourceGroup * group)
{
  GstSourceCombine *combine = NULL;
  gint pb_stream_type = -1;
  gchar *pad_name;
  GstPlayBin3 *playbin = group->playbin;

  GST_PLAY_BIN3_SHUTDOWN_LOCK (playbin, shutdown);

  pad_name = gst_object_get_name (GST_OBJECT (pad));

  GST_DEBUG_OBJECT (playbin, "decoded pad %s:%s added",
      GST_DEBUG_PAD_NAME (pad));

  /* major type of the pad, this determines the combiner to use,
     try exact match first */
  if (g_str_has_prefix (pad_name, "video")) {
    pb_stream_type = PLAYBIN_STREAM_VIDEO;
  } else if (g_str_has_prefix (pad_name, "audio")) {
    pb_stream_type = PLAYBIN_STREAM_AUDIO;
  } else if (g_str_has_prefix (pad_name, "text")) {
    pb_stream_type = PLAYBIN_STREAM_TEXT;
  }

  g_free (pad_name);

  /* no stream type found for the media type, don't bother linking it to a
   * combiner. This will leave the pad unlinked and thus ignored. */
  if (pb_stream_type < 0) {
    GST_PLAY_BIN3_SHUTDOWN_UNLOCK (playbin);
    goto unknown_type;
  }

  combine = &playbin->combiner[pb_stream_type];

  combiner_control_pad (playbin, combine, pad);

  control_source_pad (group, pad, combine->stream_type);

  /* Update present stream_types and check whether we should post a pending about-to-finish */
  group->present_stream_types |= combine->stream_type;

  if (group->playing && group->pending_about_to_finish
      && group->present_stream_types == group->selected_stream_types) {
    group->pending_about_to_finish = FALSE;
    emit_about_to_finish (playbin);
  }

  GST_PLAY_BIN3_SHUTDOWN_UNLOCK (playbin);

  return;

  /* ERRORS */
unknown_type:
  GST_DEBUG_OBJECT (playbin, "Ignoring pad with unknown type");
  return;

shutdown:
  {
    GST_DEBUG ("ignoring, we are shutting down. Pad will be left unlinked");
    /* not going to done as we didn't request the caps */
    return;
  }
}

/* called when a pad is removed from the decodebin. We unlink the pad from
 * the combiner. */
static void
pad_removed_cb (GstElement * decodebin, GstPad * pad, GstSourceGroup * group)
{
  GstSourceCombine *combine;
  GstPlayBin3 *playbin = group->playbin;

  GST_DEBUG_OBJECT (playbin,
      "decoded pad %s:%s removed", GST_DEBUG_PAD_NAME (pad));

  GST_PLAY_BIN3_LOCK (playbin);

  /* Get combiner for pad */
  if (g_str_has_prefix (GST_PAD_NAME (pad), "video"))
    combine = &playbin->combiner[PLAYBIN_STREAM_VIDEO];
  else if (g_str_has_prefix (GST_PAD_NAME (pad), "audio"))
    combine = &playbin->combiner[PLAYBIN_STREAM_AUDIO];
  else if (g_str_has_prefix (GST_PAD_NAME (pad), "text"))
    combine = &playbin->combiner[PLAYBIN_STREAM_TEXT];
  else
    return;

  combiner_release_pad (playbin, combine, pad);
  release_source_pad (playbin, group, pad);

  GST_PLAY_BIN3_UNLOCK (playbin);
}


static gint
select_stream_cb (GstElement * decodebin, GstStreamCollection * collection,
    GstStream * stream, GstSourceGroup * group)
{
  GstStreamType stype = gst_stream_get_stream_type (stream);
  GstElement *combiner = NULL;
  GstPlayBin3 *playbin = group->playbin;

  if (stype & GST_STREAM_TYPE_AUDIO)
    combiner = playbin->audio_stream_combiner;
  else if (stype & GST_STREAM_TYPE_VIDEO)
    combiner = playbin->video_stream_combiner;
  else if (stype & GST_STREAM_TYPE_TEXT)
    combiner = playbin->text_stream_combiner;

  if (combiner) {
    GST_DEBUG_OBJECT (playbin, "Got a combiner, requesting stream activation");
    return 1;
  }

  /* Let decodebin3 decide otherwise */
  return -1;
}

/* We get called when the selected stream types change and
 * reconfiguration of output (i.e. playsink and potential combiners)
 * are required.
 */
static void
reconfigure_output (GstPlayBin3 * playbin)
{
  GstPadLinkReturn res;
  gint i;

  g_assert (playbin->selected_stream_types != playbin->active_stream_types);

  GST_DEBUG_OBJECT (playbin, "selected_stream_types : %" STREAM_TYPES_FORMAT,
      STREAM_TYPES_ARGS (playbin->selected_stream_types));
  GST_DEBUG_OBJECT (playbin, "active_stream_types : %" STREAM_TYPES_FORMAT,
      STREAM_TYPES_ARGS (playbin->active_stream_types));

  GST_PLAY_BIN3_LOCK (playbin);

  /* Make sure combiners/playsink are in sync with selected stream types */
  for (i = 0; i < PLAYBIN_STREAM_LAST; i++) {
    GstSourceCombine *combine = &playbin->combiner[i];
    gboolean is_selected =
        (combine->stream_type & playbin->selected_stream_types) ==
        combine->stream_type;
    gboolean is_active =
        (combine->stream_type & playbin->active_stream_types) ==
        combine->stream_type;

    GST_DEBUG_OBJECT (playbin, "Stream type status: '%s' %s %s",
        combine->media_type, is_selected ? "selected" : "NOT selected",
        is_active ? "active" : "NOT active");
    /* FIXME : Remove asserts below once enough testing has been done */

    if (is_selected && is_active) {
      GST_DEBUG_OBJECT (playbin, "Stream type '%s' already active",
          combine->media_type);
    } else if (is_active && !is_selected) {
      GST_DEBUG_OBJECT (playbin, "Stream type '%s' is no longer requested",
          combine->media_type);

      /* Unlink combiner from sink */
      if (combine->srcpad) {
        GST_LOG_OBJECT (playbin, "Unlinking from sink");
        if (combine->sinkpad)
          gst_pad_unlink (combine->srcpad, combine->sinkpad);
        gst_object_unref (combine->srcpad);
        combine->srcpad = NULL;
      }

      if (combine->sinkpad) {
        /* Release playsink sink pad */
        GST_LOG_OBJECT (playbin, "Releasing playsink pad");
        gst_play_sink_release_pad (playbin->playsink, combine->sinkpad);
        gst_object_unref (combine->sinkpad);
        combine->sinkpad = NULL;
      }

      /* Release combiner */
      GST_FIXME_OBJECT (playbin, "Release combiner");
      remove_combiner (playbin, combine);
    } else if (!is_active && is_selected) {
      GST_DEBUG_OBJECT (playbin, "Stream type '%s' is now requested",
          combine->media_type);

      /* If we are shutting down, do *not* add more combiners */
      if (g_atomic_int_get (&playbin->shutdown))
        continue;

      g_assert (combine->sinkpad == NULL);

      /* Request playsink sink pad */
      combine->sinkpad =
          gst_play_sink_request_pad (playbin->playsink, combine->type);
      gst_object_ref (combine->sinkpad);
      /* Create combiner if needed and link it */
      create_combiner (playbin, combine);
      if (combine->combiner) {
        res = gst_pad_link (combine->srcpad, combine->sinkpad);
        GST_DEBUG_OBJECT (playbin, "linked type %s, result: %d",
            combine->media_type, res);
        if (res != GST_PAD_LINK_OK) {
          GST_ELEMENT_ERROR (playbin, CORE, PAD,
              ("Internal playbin error."),
              ("Failed to link combiner to sink. Error %d", res));
        }

      }
    }
  }

  playbin->active_stream_types = playbin->selected_stream_types;

  GST_PLAY_BIN3_UNLOCK (playbin);

  gst_play_sink_reconfigure (playbin->playsink);

  do_async_done (playbin);

  GST_DEBUG_OBJECT (playbin, "selected_stream_types : %" STREAM_TYPES_FORMAT,
      STREAM_TYPES_ARGS (playbin->selected_stream_types));
  GST_DEBUG_OBJECT (playbin, "active_stream_types : %" STREAM_TYPES_FORMAT,
      STREAM_TYPES_ARGS (playbin->active_stream_types));

  return;
}

static void
about_to_finish_cb (GstElement * uridecodebin, GstSourceGroup * group)
{
  GstPlayBin3 *playbin = group->playbin;
  GST_DEBUG_OBJECT (playbin, "about to finish in group %p", group);

  GST_LOG_OBJECT (playbin, "selected_stream_types:%" STREAM_TYPES_FORMAT,
      STREAM_TYPES_ARGS (group->selected_stream_types));
  GST_LOG_OBJECT (playbin, "present_stream_types:%" STREAM_TYPES_FORMAT,
      STREAM_TYPES_ARGS (group->present_stream_types));

  if (group->selected_stream_types == 0
      || (group->selected_stream_types != group->present_stream_types)) {
    GST_LOG_OBJECT (playbin,
        "Delaying emission of signal until this group is ready");
    group->pending_about_to_finish = TRUE;
  } else
    emit_about_to_finish (playbin);
}

#if 0                           /* AUTOPLUG DISABLED */
/* Like gst_element_factory_can_sink_any_caps() but doesn't
 * allow ANY caps on the sinkpad template */
static gboolean
_factory_can_sink_caps (GstElementFactory * factory, GstCaps * caps)
{
  const GList *templs;

  templs = gst_element_factory_get_static_pad_templates (factory);

  while (templs) {
    GstStaticPadTemplate *templ = (GstStaticPadTemplate *) templs->data;

    if (templ->direction == GST_PAD_SINK) {
      GstCaps *templcaps = gst_static_caps_get (&templ->static_caps);

      if (!gst_caps_is_any (templcaps)
          && gst_caps_is_subset (caps, templcaps)) {
        gst_caps_unref (templcaps);
        return TRUE;
      }
      gst_caps_unref (templcaps);
    }
    templs = g_list_next (templs);
  }

  return FALSE;
}

static void
avelements_free (gpointer avelement)
{
  GstAVElement *elm = (GstAVElement *) avelement;

  if (elm->dec)
    gst_object_unref (elm->dec);
  if (elm->sink)
    gst_object_unref (elm->sink);
  g_slice_free (GstAVElement, elm);
}

static gint
avelement_compare_decoder (gconstpointer p1, gconstpointer p2,
    gpointer user_data)
{
  GstAVElement *v1, *v2;

  v1 = (GstAVElement *) p1;
  v2 = (GstAVElement *) p2;

  return strcmp (GST_OBJECT_NAME (v1->dec), GST_OBJECT_NAME (v2->dec));
}

static gint
avelement_lookup_decoder (gconstpointer p1, gconstpointer p2,
    gpointer user_data)
{
  GstAVElement *v1;
  GstElementFactory *f2;

  v1 = (GstAVElement *) p1;
  f2 = (GstElementFactory *) p2;

  return strcmp (GST_OBJECT_NAME (v1->dec), GST_OBJECT_NAME (f2));
}

static gint
avelement_compare (gconstpointer p1, gconstpointer p2)
{
  GstAVElement *v1, *v2;
  GstPluginFeature *fd1, *fd2, *fs1, *fs2;
  gint64 diff, v1_rank, v2_rank;

  v1 = (GstAVElement *) p1;
  v2 = (GstAVElement *) p2;

  fd1 = (GstPluginFeature *) v1->dec;
  fd2 = (GstPluginFeature *) v2->dec;

  /* If both have a sink, we also compare their ranks */
  if (v1->sink && v2->sink) {
    fs1 = (GstPluginFeature *) v1->sink;
    fs2 = (GstPluginFeature *) v2->sink;
    v1_rank =
        gst_plugin_feature_get_rank (fd1) * gst_plugin_feature_get_rank (fs1);
    v2_rank =
        gst_plugin_feature_get_rank (fd2) * gst_plugin_feature_get_rank (fs2);
  } else {
    v1_rank = gst_plugin_feature_get_rank (fd1);
    v2_rank = gst_plugin_feature_get_rank (fd2);
    fs1 = fs2 = NULL;
  }

  /* comparison based on the rank */
  diff = v2_rank - v1_rank;
  if (diff < 0)
    return -1;
  else if (diff > 0)
    return 1;

  /* comparison based on number of common caps features */
  diff = v2->n_comm_cf - v1->n_comm_cf;
  if (diff != 0)
    return diff;

  if (fs1 && fs2) {
    /* comparison based on the name of sink elements */
    diff = strcmp (GST_OBJECT_NAME (fs1), GST_OBJECT_NAME (fs2));
    if (diff != 0)
      return diff;
  }

  /* comparison based on the name of decoder elements */
  return strcmp (GST_OBJECT_NAME (fd1), GST_OBJECT_NAME (fd2));
}

static GSequence *
avelements_create (GstPlayBin3 * playbin, gboolean isaudioelement)
{
  GstElementFactory *d_factory, *s_factory;
  GList *dec_list, *sink_list, *dl, *sl;
  GSequence *ave_seq = NULL;
  GstAVElement *ave;
  guint n_common_cf = 0;

  if (isaudioelement) {
    sink_list = gst_element_factory_list_get_elements
        (GST_ELEMENT_FACTORY_TYPE_SINK |
        GST_ELEMENT_FACTORY_TYPE_MEDIA_AUDIO, GST_RANK_MARGINAL);
    dec_list =
        gst_element_factory_list_get_elements (GST_ELEMENT_FACTORY_TYPE_DECODER
        | GST_ELEMENT_FACTORY_TYPE_MEDIA_AUDIO, GST_RANK_MARGINAL);
  } else {
    sink_list = gst_element_factory_list_get_elements
        (GST_ELEMENT_FACTORY_TYPE_SINK |
        GST_ELEMENT_FACTORY_TYPE_MEDIA_VIDEO |
        GST_ELEMENT_FACTORY_TYPE_MEDIA_IMAGE, GST_RANK_MARGINAL);

    dec_list =
        gst_element_factory_list_get_elements (GST_ELEMENT_FACTORY_TYPE_DECODER
        | GST_ELEMENT_FACTORY_TYPE_MEDIA_VIDEO |
        GST_ELEMENT_FACTORY_TYPE_MEDIA_IMAGE, GST_RANK_MARGINAL);
  }

  /* create a list of audio/video elements. Each element in the list
   * is holding an audio/video decoder and an audio/video sink in which
   * the decoders srcpad template caps and sink element's sinkpad template
   * caps are compatible */
  dl = dec_list;
  sl = sink_list;

  ave_seq = g_sequence_new ((GDestroyNotify) avelements_free);

  for (; dl; dl = dl->next) {
    d_factory = (GstElementFactory *) dl->data;
    for (; sl; sl = sl->next) {
      s_factory = (GstElementFactory *) sl->data;

      n_common_cf =
          gst_playback_utils_get_n_common_capsfeatures (d_factory, s_factory,
          gst_play_bin3_get_flags (playbin), isaudioelement);
      if (n_common_cf < 1)
        continue;

      ave = g_slice_new (GstAVElement);
      ave->dec = gst_object_ref (d_factory);
      ave->sink = gst_object_ref (s_factory);
      ave->n_comm_cf = n_common_cf;
      g_sequence_append (ave_seq, ave);
    }
    sl = sink_list;
  }
  g_sequence_sort (ave_seq, (GCompareDataFunc) avelement_compare_decoder, NULL);

  gst_plugin_feature_list_free (dec_list);
  gst_plugin_feature_list_free (sink_list);

  return ave_seq;
}

static gboolean
avelement_iter_is_equal (GSequenceIter * iter, GstElementFactory * factory)
{
  GstAVElement *ave;

  if (!iter)
    return FALSE;

  ave = g_sequence_get (iter);
  if (!ave)
    return FALSE;

  return strcmp (GST_OBJECT_NAME (ave->dec), GST_OBJECT_NAME (factory)) == 0;
}

static GList *
create_decoders_list (GList * factory_list, GSequence * avelements)
{
  GList *dec_list = NULL, *tmp;
  GList *ave_list = NULL;
  GList *ave_free_list = NULL;
  GstAVElement *ave, *best_ave;

  g_return_val_if_fail (factory_list != NULL, NULL);
  g_return_val_if_fail (avelements != NULL, NULL);

  for (tmp = factory_list; tmp; tmp = tmp->next) {
    GstElementFactory *factory = (GstElementFactory *) tmp->data;

    /* if there are parsers or sink elements, add them first */
    if (gst_element_factory_list_is_type (factory,
            GST_ELEMENT_FACTORY_TYPE_PARSER) ||
        gst_element_factory_list_is_type (factory,
            GST_ELEMENT_FACTORY_TYPE_SINK)) {
      dec_list = g_list_prepend (dec_list, gst_object_ref (factory));
    } else {
      GSequenceIter *seq_iter;

      seq_iter =
          g_sequence_lookup (avelements, factory,
          (GCompareDataFunc) avelement_lookup_decoder, NULL);
      if (!seq_iter) {
        GstAVElement *ave = g_slice_new0 (GstAVElement);

        ave->dec = factory;
        ave->sink = NULL;
        /* There's at least raw */
        ave->n_comm_cf = 1;

        ave_list = g_list_prepend (ave_list, ave);

        /* We need to free these later */
        ave_free_list = g_list_prepend (ave_free_list, ave);
        continue;
      }

      /* Go to first iter with that decoder */
      do {
        GSequenceIter *tmp_seq_iter;

        tmp_seq_iter = g_sequence_iter_prev (seq_iter);
        if (!avelement_iter_is_equal (tmp_seq_iter, factory))
          break;
        seq_iter = tmp_seq_iter;
      } while (!g_sequence_iter_is_begin (seq_iter));

      /* Get the best ranked GstAVElement for that factory */
      best_ave = NULL;
      while (!g_sequence_iter_is_end (seq_iter)
          && avelement_iter_is_equal (seq_iter, factory)) {
        ave = g_sequence_get (seq_iter);

        if (!best_ave || avelement_compare (ave, best_ave) < 0)
          best_ave = ave;

        seq_iter = g_sequence_iter_next (seq_iter);
      }
      ave_list = g_list_prepend (ave_list, best_ave);
    }
  }

  /* Sort all GstAVElements by their relative ranks and insert
   * into the decoders list */
  ave_list = g_list_sort (ave_list, (GCompareFunc) avelement_compare);
  for (tmp = ave_list; tmp; tmp = tmp->next) {
    ave = (GstAVElement *) tmp->data;
    dec_list = g_list_prepend (dec_list, gst_object_ref (ave->dec));
  }
  g_list_free (ave_list);
  gst_plugin_feature_list_free (factory_list);

  for (tmp = ave_free_list; tmp; tmp = tmp->next)
    g_slice_free (GstAVElement, tmp->data);
  g_list_free (ave_free_list);

  dec_list = g_list_reverse (dec_list);

  return dec_list;
}

/* Called when we must provide a list of factories to plug to @pad with @caps.
 * We first check if we have a sink that can handle the format and if we do, we
 * return NULL, to expose the pad. If we have no sink (or the sink does not
 * work), we return the list of elements that can connect. */
static GValueArray *
autoplug_factories_cb (GstElement * decodebin, GstPad * pad,
    GstCaps * caps, GstSourceGroup * group)
{
  GstPlayBin3 *playbin;
  GList *factory_list, *tmp;
  GValueArray *result;
  gboolean unref_caps = FALSE;
  gboolean isaudiodeclist = FALSE;
  gboolean isvideodeclist = FALSE;

  if (!caps) {
    caps = gst_caps_new_any ();
    unref_caps = TRUE;
  }

  playbin = group->playbin;

  GST_DEBUG_OBJECT (playbin, "factories group %p for %s:%s, %" GST_PTR_FORMAT,
      group, GST_DEBUG_PAD_NAME (pad), caps);

  /* filter out the elements based on the caps. */
  g_mutex_lock (&playbin->elements_lock);
  gst_play_bin3_update_elements_list (playbin);
  factory_list =
      gst_element_factory_list_filter (playbin->elements, caps, GST_PAD_SINK,
      gst_caps_is_fixed (caps));
  g_mutex_unlock (&playbin->elements_lock);

  GST_DEBUG_OBJECT (playbin, "found factories %p", factory_list);
  GST_PLUGIN_FEATURE_LIST_DEBUG (factory_list);

  /* check whether the caps are asking for a list of audio/video decoders */
  tmp = factory_list;
  if (!gst_caps_is_any (caps)) {
    for (; tmp; tmp = tmp->next) {
      GstElementFactory *factory = (GstElementFactory *) tmp->data;

      isvideodeclist = gst_element_factory_list_is_type (factory,
          GST_ELEMENT_FACTORY_TYPE_DECODER |
          GST_ELEMENT_FACTORY_TYPE_MEDIA_VIDEO |
          GST_ELEMENT_FACTORY_TYPE_MEDIA_IMAGE);
      isaudiodeclist = gst_element_factory_list_is_type (factory,
          GST_ELEMENT_FACTORY_TYPE_DECODER |
          GST_ELEMENT_FACTORY_TYPE_MEDIA_AUDIO);

      if (isaudiodeclist || isvideodeclist)
        break;
    }
  }

  if (isaudiodeclist || isvideodeclist) {
    GSequence **ave_list;
    if (isaudiodeclist)
      ave_list = &playbin->aelements;
    else
      ave_list = &playbin->velements;

    g_mutex_lock (&playbin->elements_lock);
    /* sort factory_list based on the GstAVElement list priority */
    factory_list = create_decoders_list (factory_list, *ave_list);
    g_mutex_unlock (&playbin->elements_lock);
  }

  /* 2 additional elements for the already set audio/video sinks */
  result = g_value_array_new (g_list_length (factory_list) + 2);

  /* Check if we already have an audio/video sink and if this is the case
   * put it as the first element of the array */
  if (group->audio_sink) {
    GstElementFactory *factory = gst_element_get_factory (group->audio_sink);

    if (factory && _factory_can_sink_caps (factory, caps)) {
      GValue val = { 0, };

      g_value_init (&val, G_TYPE_OBJECT);
      g_value_set_object (&val, factory);
      result = g_value_array_append (result, &val);
      g_value_unset (&val);
    }
  }

  if (group->video_sink) {
    GstElementFactory *factory = gst_element_get_factory (group->video_sink);

    if (factory && _factory_can_sink_caps (factory, caps)) {
      GValue val = { 0, };

      g_value_init (&val, G_TYPE_OBJECT);
      g_value_set_object (&val, factory);
      result = g_value_array_append (result, &val);
      g_value_unset (&val);
    }
  }

  for (tmp = factory_list; tmp; tmp = tmp->next) {
    GstElementFactory *factory = GST_ELEMENT_FACTORY_CAST (tmp->data);
    GValue val = { 0, };

    if (group->audio_sink && gst_element_factory_list_is_type (factory,
            GST_ELEMENT_FACTORY_TYPE_SINK |
            GST_ELEMENT_FACTORY_TYPE_MEDIA_AUDIO)) {
      continue;
    }
    if (group->video_sink && gst_element_factory_list_is_type (factory,
            GST_ELEMENT_FACTORY_TYPE_SINK | GST_ELEMENT_FACTORY_TYPE_MEDIA_VIDEO
            | GST_ELEMENT_FACTORY_TYPE_MEDIA_IMAGE)) {
      continue;
    }

    g_value_init (&val, G_TYPE_OBJECT);
    g_value_set_object (&val, factory);
    g_value_array_append (result, &val);
    g_value_unset (&val);
  }
  gst_plugin_feature_list_free (factory_list);

  if (unref_caps)
    gst_caps_unref (caps);

  return result;
}
#endif

static GstBusSyncReply
activate_sink_bus_handler (GstBus * bus, GstMessage * msg,
    GstPlayBin3 * playbin)
{
  if (GST_MESSAGE_TYPE (msg) == GST_MESSAGE_ERROR) {
    /* Only proxy errors from a fixed sink. If that fails we can just error out
     * early as stuff will fail later anyway */
    if (playbin->audio_sink
        && gst_object_has_as_ancestor (GST_MESSAGE_SRC (msg),
            GST_OBJECT_CAST (playbin->audio_sink)))
      gst_element_post_message (GST_ELEMENT_CAST (playbin), msg);
    else if (playbin->video_sink
        && gst_object_has_as_ancestor (GST_MESSAGE_SRC (msg),
            GST_OBJECT_CAST (playbin->video_sink)))
      gst_element_post_message (GST_ELEMENT_CAST (playbin), msg);
    else if (playbin->text_sink
        && gst_object_has_as_ancestor (GST_MESSAGE_SRC (msg),
            GST_OBJECT_CAST (playbin->text_sink)))
      gst_element_post_message (GST_ELEMENT_CAST (playbin), msg);
    else
      gst_message_unref (msg);
  } else {
    gst_element_post_message (GST_ELEMENT_CAST (playbin), msg);
  }

  /* Doesn't really matter, nothing is using this bus */
  return GST_BUS_DROP;
}

static gboolean
activate_sink (GstPlayBin3 * playbin, GstElement * sink, gboolean * activated)
{
  GstState state;
  GstBus *bus = NULL;
  GstStateChangeReturn sret;
  gboolean ret = FALSE;

  if (activated)
    *activated = FALSE;

  GST_OBJECT_LOCK (sink);
  state = GST_STATE (sink);
  GST_OBJECT_UNLOCK (sink);
  if (state >= GST_STATE_READY) {
    ret = TRUE;
    goto done;
  }

  if (!GST_OBJECT_PARENT (sink)) {
    bus = gst_bus_new ();
    gst_bus_set_sync_handler (bus,
        (GstBusSyncHandler) activate_sink_bus_handler, playbin, NULL);
    gst_element_set_bus (sink, bus);
  }

  sret = gst_element_set_state (sink, GST_STATE_READY);
  if (sret == GST_STATE_CHANGE_FAILURE)
    goto done;

  if (activated)
    *activated = TRUE;
  ret = TRUE;

done:
  if (bus) {
    gst_element_set_bus (sink, NULL);
    gst_object_unref (bus);
  }

  return ret;
}

#if 0                           /* AUTOPLUG DISABLED */
/* autoplug-continue decides, if a pad has raw caps that can be exposed
 * directly or if further decoding is necessary. We use this to expose
 * supported subtitles directly */

/* FIXME 0.11: Remove the checks for ANY caps, a sink should specify
 * explicitly the caps it supports and if it claims to support ANY
 * caps it really should support everything */
static gboolean
autoplug_continue_cb (GstElement * element, GstPad * pad, GstCaps * caps,
    GstSourceGroup * group)
{
  gboolean ret = TRUE;
  GstPad *sinkpad = NULL;
  gboolean activated_sink;

  GST_SOURCE_GROUP_LOCK (group);

  if (group->text_sink &&
      activate_sink (group->playbin, group->text_sink, &activated_sink)) {
    sinkpad = gst_element_get_static_pad (group->text_sink, "sink");
    if (sinkpad) {
      GstCaps *sinkcaps;

      sinkcaps = gst_pad_query_caps (sinkpad, NULL);
      if (!gst_caps_is_any (sinkcaps))
        ret = !gst_pad_query_accept_caps (sinkpad, caps);
      gst_caps_unref (sinkcaps);
      gst_object_unref (sinkpad);
    }
    if (activated_sink)
      gst_element_set_state (group->text_sink, GST_STATE_NULL);
  } else {
    GstCaps *subcaps = gst_subtitle_overlay_create_factory_caps ();
    ret = !gst_caps_is_subset (caps, subcaps);
    gst_caps_unref (subcaps);
  }
  /* If autoplugging can stop don't do additional checks */
  if (!ret)
    goto done;

  if (group->audio_sink &&
      activate_sink (group->playbin, group->audio_sink, &activated_sink)) {

    sinkpad = gst_element_get_static_pad (group->audio_sink, "sink");
    if (sinkpad) {
      GstCaps *sinkcaps;

      sinkcaps = gst_pad_query_caps (sinkpad, NULL);
      if (!gst_caps_is_any (sinkcaps))
        ret = !gst_pad_query_accept_caps (sinkpad, caps);
      gst_caps_unref (sinkcaps);
      gst_object_unref (sinkpad);
    }
    if (activated_sink)
      gst_element_set_state (group->audio_sink, GST_STATE_NULL);
  }
  if (!ret)
    goto done;

  if (group->video_sink
      && activate_sink (group->playbin, group->video_sink, &activated_sink)) {
    sinkpad = gst_element_get_static_pad (group->video_sink, "sink");
    if (sinkpad) {
      GstCaps *sinkcaps;

      sinkcaps = gst_pad_query_caps (sinkpad, NULL);
      if (!gst_caps_is_any (sinkcaps))
        ret = !gst_pad_query_accept_caps (sinkpad, caps);
      gst_caps_unref (sinkcaps);
      gst_object_unref (sinkpad);
    }
    if (activated_sink)
      gst_element_set_state (group->video_sink, GST_STATE_NULL);
  }

done:
  GST_SOURCE_GROUP_UNLOCK (group);

  GST_DEBUG_OBJECT (group->playbin,
      "continue autoplugging group %p for %s:%s, %" GST_PTR_FORMAT ": %d",
      group, GST_DEBUG_PAD_NAME (pad), caps, ret);

  return ret;
}

static gboolean
sink_accepts_caps (GstPlayBin3 * playbin, GstElement * sink, GstCaps * caps)
{
  GstPad *sinkpad;

  if ((sinkpad = gst_element_get_static_pad (sink, "sink"))) {
    /* Got the sink pad, now let's see if the element actually does accept the
     * caps that we have */
    if (!gst_pad_query_accept_caps (sinkpad, caps)) {
      gst_object_unref (sinkpad);
      return FALSE;
    }
    gst_object_unref (sinkpad);
  }

  return TRUE;
}

/* We are asked to select an element. See if the next element to check
 * is a sink. If this is the case, we see if the sink works by setting it to
 * READY. If the sink works, we return SELECT_EXPOSE to make decodebin
 * expose the raw pad so that we can setup the mixers. */
static GstAutoplugSelectResult
autoplug_select_cb (GstElement * decodebin, GstPad * pad,
    GstCaps * caps, GstElementFactory * factory, GstSourceGroup * group)
{
  GstPlayBin3 *playbin;
  GstElement *element;
  const gchar *klass;
  GstPlaySinkType type;
  GstElement **sinkp;
  GList *ave_list = NULL, *l;
  GstAVElement *ave = NULL;
  GSequence *ave_seq = NULL;
  GSequenceIter *seq_iter;

  playbin = group->playbin;

  GST_DEBUG_OBJECT (playbin, "select group %p for %s:%s, %" GST_PTR_FORMAT,
      group, GST_DEBUG_PAD_NAME (pad), caps);

  GST_DEBUG_OBJECT (playbin, "checking factory %s", GST_OBJECT_NAME (factory));

  /* if it's not a sink, we make sure the element is compatible with
   * the fixed sink */
  if (!gst_element_factory_list_is_type (factory,
          GST_ELEMENT_FACTORY_TYPE_SINK)) {
    gboolean isvideodec = gst_element_factory_list_is_type (factory,
        GST_ELEMENT_FACTORY_TYPE_DECODER |
        GST_ELEMENT_FACTORY_TYPE_MEDIA_VIDEO |
        GST_ELEMENT_FACTORY_TYPE_MEDIA_IMAGE);
    gboolean isaudiodec = gst_element_factory_list_is_type (factory,
        GST_ELEMENT_FACTORY_TYPE_DECODER |
        GST_ELEMENT_FACTORY_TYPE_MEDIA_AUDIO);

    if (!isvideodec && !isaudiodec)
      return GST_AUTOPLUG_SELECT_TRY;

    GST_SOURCE_GROUP_LOCK (group);
    g_mutex_lock (&playbin->elements_lock);

    if (isaudiodec) {
      ave_seq = playbin->aelements;
      sinkp = &group->audio_sink;
    } else {
      ave_seq = playbin->velements;
      sinkp = &group->video_sink;
    }

    seq_iter =
        g_sequence_lookup (ave_seq, factory,
        (GCompareDataFunc) avelement_lookup_decoder, NULL);
    if (seq_iter) {
      /* Go to first iter with that decoder */
      do {
        GSequenceIter *tmp_seq_iter;

        tmp_seq_iter = g_sequence_iter_prev (seq_iter);
        if (!avelement_iter_is_equal (tmp_seq_iter, factory))
          break;
        seq_iter = tmp_seq_iter;
      } while (!g_sequence_iter_is_begin (seq_iter));

      while (!g_sequence_iter_is_end (seq_iter)
          && avelement_iter_is_equal (seq_iter, factory)) {
        ave = g_sequence_get (seq_iter);
        ave_list = g_list_prepend (ave_list, ave);
        seq_iter = g_sequence_iter_next (seq_iter);
      }

      /* Sort all GstAVElements by their relative ranks and insert
       * into the decoders list */
      ave_list = g_list_sort (ave_list, (GCompareFunc) avelement_compare);
    } else {
      ave_list = g_list_prepend (ave_list, NULL);
    }

    /* if it is a decoder and we don't have a fixed sink, then find out
     * the matching audio/video sink from GstAVElements list */
    for (l = ave_list; l; l = l->next) {
      gboolean created_sink = FALSE;

      ave = (GstAVElement *) l->data;

      if (((isaudiodec && !group->audio_sink) ||
              (isvideodec && !group->video_sink))) {
        if (ave && ave->sink) {
          GST_DEBUG_OBJECT (playbin,
              "Trying to create sink '%s' for decoder '%s'",
              gst_plugin_feature_get_name (GST_PLUGIN_FEATURE (ave->sink)),
              gst_plugin_feature_get_name (GST_PLUGIN_FEATURE (factory)));
          if ((*sinkp = gst_element_factory_create (ave->sink, NULL)) == NULL) {
            GST_WARNING_OBJECT (playbin,
                "Could not create an element from %s",
                gst_plugin_feature_get_name (GST_PLUGIN_FEATURE (ave->sink)));
            continue;
          } else {
            if (!activate_sink (playbin, *sinkp, NULL)) {
              gst_object_unref (*sinkp);
              *sinkp = NULL;
              GST_WARNING_OBJECT (playbin,
                  "Could not activate sink %s",
                  gst_plugin_feature_get_name (GST_PLUGIN_FEATURE (ave->sink)));
              continue;
            }
            gst_object_ref_sink (*sinkp);
            created_sink = TRUE;
          }
        }
      }

      /* If it is a decoder and we have a fixed sink for the media
       * type it outputs, check that the decoder is compatible with this sink */
      if ((isaudiodec && group->audio_sink) || (isvideodec
              && group->video_sink)) {
        gboolean compatible = FALSE;
        GstPad *sinkpad;
        GstCaps *caps;
        GstElement *sink;

        sink = *sinkp;

        if ((sinkpad = gst_element_get_static_pad (sink, "sink"))) {
          GstPlayFlags flags = gst_play_bin3_get_flags (playbin);
          GstCaps *raw_caps =
              (isaudiodec) ? gst_static_caps_get (&raw_audio_caps) :
              gst_static_caps_get (&raw_video_caps);

          caps = gst_pad_query_caps (sinkpad, NULL);

          /* If the sink supports raw audio/video, we first check
           * if the decoder could output any raw audio/video format
           * and assume it is compatible with the sink then. We don't
           * do a complete compatibility check here if converters
           * are plugged between the decoder and the sink because
           * the converters will convert between raw formats and
           * even if the decoder format is not supported by the decoder
           * a converter will convert it.
           *
           * We assume here that the converters can convert between
           * any raw format.
           */
          if ((isaudiodec && !(flags & GST_PLAY_FLAG_NATIVE_AUDIO)
                  && gst_caps_can_intersect (caps, raw_caps)) || (!isaudiodec
                  && !(flags & GST_PLAY_FLAG_NATIVE_VIDEO)
                  && gst_caps_can_intersect (caps, raw_caps))) {
            compatible =
                gst_element_factory_can_src_any_caps (factory, raw_caps)
                || gst_element_factory_can_src_any_caps (factory, caps);
          } else {
            compatible = gst_element_factory_can_src_any_caps (factory, caps);
          }

          gst_object_unref (sinkpad);
          gst_caps_unref (caps);
        }

        if (compatible)
          break;

        GST_DEBUG_OBJECT (playbin, "%s not compatible with the fixed sink",
            GST_OBJECT_NAME (factory));

        /* If it is not compatible, either continue with the next possible
         * sink or if we have a fixed sink, skip the decoder */
        if (created_sink) {
          gst_element_set_state (*sinkp, GST_STATE_NULL);
          gst_object_unref (*sinkp);
          *sinkp = NULL;
        } else {
          g_mutex_unlock (&playbin->elements_lock);
          GST_SOURCE_GROUP_UNLOCK (group);
          return GST_AUTOPLUG_SELECT_SKIP;
        }
      }
    }
    g_list_free (ave_list);
    g_mutex_unlock (&playbin->elements_lock);
    GST_SOURCE_GROUP_UNLOCK (group);
    return GST_AUTOPLUG_SELECT_TRY;
  }

  /* it's a sink, see if an instance of it actually works */
  GST_DEBUG_OBJECT (playbin, "we found a sink '%s'", GST_OBJECT_NAME (factory));

  klass =
      gst_element_factory_get_metadata (factory, GST_ELEMENT_METADATA_KLASS);

  /* figure out the klass */
  if (strstr (klass, "Audio")) {
    GST_DEBUG_OBJECT (playbin, "we found an audio sink");
    type = GST_PLAY_SINK_TYPE_AUDIO;
    sinkp = &group->audio_sink;
  } else if (strstr (klass, "Video")) {
    GST_DEBUG_OBJECT (playbin, "we found a video sink");
    type = GST_PLAY_SINK_TYPE_VIDEO;
    sinkp = &group->video_sink;
  } else {
    /* unknown klass, skip this element */
    GST_WARNING_OBJECT (playbin, "unknown sink klass %s found", klass);
    return GST_AUTOPLUG_SELECT_SKIP;
  }

  /* if we are asked to do visualisations and it's an audio sink, skip the
   * element. We can only do visualisations with raw sinks */
  if (gst_play_sink_get_flags (playbin->playsink) & GST_PLAY_FLAG_VIS) {
    if (type == GST_PLAY_SINK_TYPE_AUDIO) {
      GST_DEBUG_OBJECT (playbin, "skip audio sink because of vis");
      return GST_AUTOPLUG_SELECT_SKIP;
    }
  }

  /* now see if we already have a sink element */
  GST_SOURCE_GROUP_LOCK (group);
  if (*sinkp && GST_STATE (*sinkp) >= GST_STATE_READY) {
    GstElement *sink = gst_object_ref (*sinkp);

    if (sink_accepts_caps (playbin, sink, caps)) {
      GST_DEBUG_OBJECT (playbin,
          "Existing sink '%s' accepts caps: %" GST_PTR_FORMAT,
          GST_ELEMENT_NAME (sink), caps);
      gst_object_unref (sink);
      GST_SOURCE_GROUP_UNLOCK (group);
      return GST_AUTOPLUG_SELECT_EXPOSE;
    } else {
      GST_DEBUG_OBJECT (playbin,
          "Existing sink '%s' does not accept caps: %" GST_PTR_FORMAT,
          GST_ELEMENT_NAME (sink), caps);
      gst_object_unref (sink);
      GST_SOURCE_GROUP_UNLOCK (group);
      return GST_AUTOPLUG_SELECT_SKIP;
    }
  }
  GST_DEBUG_OBJECT (playbin, "we have no pending sink, try to create '%s'",
      gst_plugin_feature_get_name (GST_PLUGIN_FEATURE (factory)));

  if ((*sinkp = gst_element_factory_create (factory, NULL)) == NULL) {
    GST_WARNING_OBJECT (playbin, "Could not create an element from %s",
        gst_plugin_feature_get_name (GST_PLUGIN_FEATURE (factory)));
    GST_SOURCE_GROUP_UNLOCK (group);
    return GST_AUTOPLUG_SELECT_SKIP;
  }

  element = *sinkp;

  if (!activate_sink (playbin, element, NULL)) {
    GST_WARNING_OBJECT (playbin, "Could not activate sink %s",
        gst_plugin_feature_get_name (GST_PLUGIN_FEATURE (factory)));
    *sinkp = NULL;
    gst_object_unref (element);
    GST_SOURCE_GROUP_UNLOCK (group);
    return GST_AUTOPLUG_SELECT_SKIP;
  }

  /* Check if the selected sink actually supports the
   * caps and can be set to READY*/
  if (!sink_accepts_caps (playbin, element, caps)) {
    *sinkp = NULL;
    gst_element_set_state (element, GST_STATE_NULL);
    gst_object_unref (element);
    GST_SOURCE_GROUP_UNLOCK (group);
    return GST_AUTOPLUG_SELECT_SKIP;
  }

  /* remember the sink in the group now, the element is floating, we take
   * ownership now
   *
   * store the sink in the group, we will configure it later when we
   * reconfigure the sink */
  GST_DEBUG_OBJECT (playbin, "remember sink");
  gst_object_ref_sink (element);
  GST_SOURCE_GROUP_UNLOCK (group);

  /* tell decodebin to expose the pad because we are going to use this
   * sink */
  GST_DEBUG_OBJECT (playbin, "we found a working sink, expose pad");

  return GST_AUTOPLUG_SELECT_EXPOSE;
}

#define GST_PLAY_BIN3_FILTER_CAPS(filter,caps) G_STMT_START {                  \
  if ((filter)) {                                                             \
    GstCaps *intersection =                                                   \
        gst_caps_intersect_full ((filter), (caps), GST_CAPS_INTERSECT_FIRST); \
    gst_caps_unref ((caps));                                                  \
    (caps) = intersection;                                                    \
  }                                                                           \
} G_STMT_END

static gboolean
autoplug_query_caps (GstElement * uridecodebin, GstPad * pad,
    GstElement * element, GstQuery * query, GstSourceGroup * group)
{
  GstCaps *filter, *result = NULL;
  GstElement *sink;
  GstPad *sinkpad = NULL;
  GstElementFactory *factory;
  GstElementFactoryListType factory_type;
  gboolean have_sink = FALSE;

  GST_SOURCE_GROUP_LOCK (group);
  gst_query_parse_caps (query, &filter);

  factory = gst_element_get_factory (element);
  if (!factory)
    goto done;

  if (gst_element_factory_list_is_type (factory,
          GST_ELEMENT_FACTORY_TYPE_MEDIA_VIDEO |
          GST_ELEMENT_FACTORY_TYPE_MEDIA_IMAGE)) {
    factory_type =
        GST_ELEMENT_FACTORY_TYPE_MEDIA_VIDEO |
        GST_ELEMENT_FACTORY_TYPE_MEDIA_IMAGE;

    if ((sink = group->video_sink)) {
      sinkpad = gst_element_get_static_pad (sink, "sink");
      if (sinkpad) {
        GstCaps *sinkcaps;

        sinkcaps = gst_pad_query_caps (sinkpad, filter);
        if (!gst_caps_is_any (sinkcaps)) {
          if (!result)
            result = sinkcaps;
          else
            result = gst_caps_merge (result, sinkcaps);
        } else {
          gst_caps_unref (sinkcaps);
        }
        gst_object_unref (sinkpad);
      }
      have_sink = TRUE;
    }
  } else if (gst_element_factory_list_is_type (factory,
          GST_ELEMENT_FACTORY_TYPE_MEDIA_AUDIO)) {
    factory_type = GST_ELEMENT_FACTORY_TYPE_MEDIA_AUDIO;

    if ((sink = group->audio_sink)) {
      sinkpad = gst_element_get_static_pad (sink, "sink");
      if (sinkpad) {
        GstCaps *sinkcaps;

        sinkcaps = gst_pad_query_caps (sinkpad, filter);
        if (!gst_caps_is_any (sinkcaps)) {
          if (!result)
            result = sinkcaps;
          else
            result = gst_caps_merge (result, sinkcaps);
        } else {
          gst_caps_unref (sinkcaps);
        }
        gst_object_unref (sinkpad);
      }
      have_sink = TRUE;
    }
  } else if (gst_element_factory_list_is_type (factory,
          GST_ELEMENT_FACTORY_TYPE_MEDIA_SUBTITLE)) {
    factory_type = GST_ELEMENT_FACTORY_TYPE_MEDIA_SUBTITLE;

    if ((sink = group->playbin->text_sink)) {
      sinkpad = gst_element_get_static_pad (sink, "sink");
      if (sinkpad) {
        GstCaps *sinkcaps;

        sinkcaps = gst_pad_query_caps (sinkpad, filter);
        if (!gst_caps_is_any (sinkcaps)) {
          if (!result)
            result = sinkcaps;
          else
            result = gst_caps_merge (result, sinkcaps);
        } else {
          gst_caps_unref (sinkcaps);
        }
        gst_object_unref (sinkpad);
      }
      have_sink = TRUE;
    } else {
      GstCaps *subcaps = gst_subtitle_overlay_create_factory_caps ();
      GST_PLAY_BIN3_FILTER_CAPS (filter, subcaps);
      if (!result)
        result = subcaps;
      else
        result = gst_caps_merge (result, subcaps);
    }
  } else {
    goto done;
  }

  if (!have_sink) {
    GValueArray *factories;
    gint i, n;

    factories = autoplug_factories_cb (uridecodebin, pad, NULL, group);
    n = factories->n_values;
    for (i = 0; i < n; i++) {
      GValue *v = g_value_array_get_nth (factories, i);
      GstElementFactory *f = g_value_get_object (v);
      const GList *templates;
      const GList *l;
      GstCaps *templ_caps;

      if (!gst_element_factory_list_is_type (f, factory_type))
        continue;

      templates = gst_element_factory_get_static_pad_templates (f);

      for (l = templates; l; l = l->next) {
        templ_caps = gst_static_pad_template_get_caps (l->data);

        if (!gst_caps_is_any (templ_caps)) {
          GST_PLAY_BIN3_FILTER_CAPS (filter, templ_caps);
          if (!result)
            result = templ_caps;
          else
            result = gst_caps_merge (result, templ_caps);
        } else {
          gst_caps_unref (templ_caps);
        }
      }
    }
    g_value_array_free (factories);
  }

done:
  GST_SOURCE_GROUP_UNLOCK (group);

  if (!result)
    return FALSE;

  /* Add the actual decoder/parser/etc caps at the very end to
   * make sure we don't cause empty caps to be returned, e.g.
   * if a parser asks us but a decoder is required after it
   * because no sink can handle the format directly.
   */
  {
    GstPad *target = gst_ghost_pad_get_target (GST_GHOST_PAD (pad));

    if (target) {
      GstCaps *target_caps = gst_pad_get_pad_template_caps (target);
      GST_PLAY_BIN3_FILTER_CAPS (filter, target_caps);
      result = gst_caps_merge (result, target_caps);
      gst_object_unref (target);
    }
  }


  gst_query_set_caps_result (query, result);
  gst_caps_unref (result);

  return TRUE;
}

static gboolean
autoplug_query_context (GstElement * uridecodebin, GstPad * pad,
    GstElement * element, GstQuery * query, GstSourceGroup * group)
{
  GstElement *sink;
  GstPad *sinkpad = NULL;
  GstElementFactory *factory;
  gboolean res = FALSE;

  GST_SOURCE_GROUP_LOCK (group);

  factory = gst_element_get_factory (element);
  if (!factory)
    goto done;

  if (gst_element_factory_list_is_type (factory,
          GST_ELEMENT_FACTORY_TYPE_MEDIA_VIDEO |
          GST_ELEMENT_FACTORY_TYPE_MEDIA_IMAGE)) {
    if ((sink = group->video_sink)) {
      sinkpad = gst_element_get_static_pad (sink, "sink");
      if (sinkpad) {
        res = gst_pad_query (sinkpad, query);
        gst_object_unref (sinkpad);
      }
    }
  } else if (gst_element_factory_list_is_type (factory,
          GST_ELEMENT_FACTORY_TYPE_MEDIA_AUDIO)) {
    if ((sink = group->audio_sink)) {
      sinkpad = gst_element_get_static_pad (sink, "sink");
      if (sinkpad) {
        res = gst_pad_query (sinkpad, query);
        gst_object_unref (sinkpad);
      }
    }
  } else if (gst_element_factory_list_is_type (factory,
          GST_ELEMENT_FACTORY_TYPE_MEDIA_SUBTITLE)) {
    if ((sink = group->playbin->text_sink)) {
      sinkpad = gst_element_get_static_pad (sink, "sink");
      if (sinkpad) {
        res = gst_pad_query (sinkpad, query);
        gst_object_unref (sinkpad);
      }
    }
  } else {
    goto done;
  }

done:
  GST_SOURCE_GROUP_UNLOCK (group);

  return res;
}

static gboolean
autoplug_query_cb (GstElement * uridecodebin, GstPad * pad,
    GstElement * element, GstQuery * query, GstSourceGroup * group)
{

  switch (GST_QUERY_TYPE (query)) {
    case GST_QUERY_CAPS:
      return autoplug_query_caps (uridecodebin, pad, element, query, group);
    case GST_QUERY_CONTEXT:
      return autoplug_query_context (uridecodebin, pad, element, query, group);
    default:
      return FALSE;
  }
}
#endif

/* must be called with the group lock */
static gboolean
group_set_locked_state_unlocked (GstPlayBin3 * playbin, GstSourceGroup * group,
    gboolean locked)
{
  GST_DEBUG_OBJECT (playbin, "locked_state %d on group %p", locked, group);

  if (group->uridecodebin)
    gst_element_set_locked_state (group->uridecodebin, locked);

  return TRUE;
}

static gboolean
make_or_reuse_element (GstPlayBin3 * playbin, const gchar * name,
    GstElement ** elem)
{
  if (*elem) {
    GST_DEBUG_OBJECT (playbin, "reusing existing %s", name);
    gst_element_set_state (*elem, GST_STATE_READY);
    /* no need to take extra ref, we already have one
     * and the bin will add one since it is no longer floating,
     * as we added a non-floating ref when removing it from the
     * bin earlier */
  } else {
    GstElement *new_elem;
    GST_DEBUG_OBJECT (playbin, "making new %s", name);
    new_elem = gst_element_factory_make (name, NULL);
    if (!new_elem)
      return FALSE;
    *elem = gst_object_ref (new_elem);
  }

  if (GST_OBJECT_PARENT (*elem) != GST_OBJECT_CAST (playbin))
    gst_bin_add (GST_BIN_CAST (playbin), *elem);
  return TRUE;
}


static void
source_setup_cb (GstElement * element, GstElement * source,
    GstSourceGroup * group)
{
  g_signal_emit (group->playbin, gst_play_bin3_signals[SIGNAL_SOURCE_SETUP], 0,
      source);
}

/* must be called with PLAY_BIN_LOCK */
static GstStateChangeReturn
activate_group (GstPlayBin3 * playbin, GstSourceGroup * group)
{
  GstElement *uridecodebin = NULL;
  GstPlayFlags flags;
  gboolean audio_sink_activated = FALSE;
  gboolean video_sink_activated = FALSE;
  gboolean text_sink_activated = FALSE;
  GstStateChangeReturn state_ret;

  g_return_val_if_fail (group->valid, GST_STATE_CHANGE_FAILURE);
  g_return_val_if_fail (!group->active, GST_STATE_CHANGE_FAILURE);

  GST_DEBUG_OBJECT (playbin, "activating group %p", group);

  GST_SOURCE_GROUP_LOCK (group);

  /* First set up the custom sinks */
  if (playbin->audio_sink)
    group->audio_sink = gst_object_ref (playbin->audio_sink);
  else
    group->audio_sink =
        gst_play_sink_get_sink (playbin->playsink, GST_PLAY_SINK_TYPE_AUDIO);

  if (group->audio_sink) {
    if (!activate_sink (playbin, group->audio_sink, &audio_sink_activated)) {
      if (group->audio_sink == playbin->audio_sink) {
        goto sink_failure;
      } else {
        gst_object_unref (group->audio_sink);
        group->audio_sink = NULL;
      }
    }
  }

  if (playbin->video_sink)
    group->video_sink = gst_object_ref (playbin->video_sink);
  else
    group->video_sink =
        gst_play_sink_get_sink (playbin->playsink, GST_PLAY_SINK_TYPE_VIDEO);

  if (group->video_sink) {
    if (!activate_sink (playbin, group->video_sink, &video_sink_activated)) {
      if (group->video_sink == playbin->video_sink) {
        goto sink_failure;
      } else {
        gst_object_unref (group->video_sink);
        group->video_sink = NULL;
      }
    }
  }

  if (playbin->text_sink)
    group->text_sink = gst_object_ref (playbin->text_sink);
  else
    group->text_sink =
        gst_play_sink_get_sink (playbin->playsink, GST_PLAY_SINK_TYPE_TEXT);

  if (group->text_sink) {
    if (!activate_sink (playbin, group->text_sink, &text_sink_activated)) {
      if (group->text_sink == playbin->text_sink) {
        goto sink_failure;
      } else {
        gst_object_unref (group->text_sink);
        group->text_sink = NULL;
      }
    }
  }


  if (!make_or_reuse_element (playbin, "uridecodebin3", &group->uridecodebin))
    goto no_uridecodebin;
  uridecodebin = group->uridecodebin;

  flags = gst_play_sink_get_flags (playbin->playsink);

  g_object_set (uridecodebin,
      /* configure connection speed */
      "connection-speed", playbin->connection_speed / 1000,
      /* configure uri */
      "uri", group->uri,
      /* configure download buffering */
      "download", ((flags & GST_PLAY_FLAG_DOWNLOAD) != 0),
      /* configure buffering of demuxed/parsed data */
      "use-buffering", ((flags & GST_PLAY_FLAG_BUFFERING) != 0),
      /* configure buffering parameters */
      "buffer-duration", playbin->buffer_duration,
      "buffer-size", playbin->buffer_size,
      "ring-buffer-max-size", playbin->ring_buffer_max_size, NULL);

  group->pad_added_id = g_signal_connect (uridecodebin, "pad-added",
      G_CALLBACK (pad_added_cb), group);
  group->pad_removed_id = g_signal_connect (uridecodebin,
      "pad-removed", G_CALLBACK (pad_removed_cb), group);
  group->select_stream_id = g_signal_connect (uridecodebin, "select-stream",
      G_CALLBACK (select_stream_cb), group);
  group->source_setup_id = g_signal_connect (uridecodebin, "source-setup",
      G_CALLBACK (source_setup_cb), group);
  group->about_to_finish_id =
      g_signal_connect (uridecodebin, "about-to-finish",
      G_CALLBACK (about_to_finish_cb), group);

  if (group->suburi)
    g_object_set (group->uridecodebin, "suburi", group->suburi, NULL);

  /* release the group lock before setting the state of the source bins, they
   * might fire signals in this thread that we need to handle with the
   * group_lock taken. */
  GST_SOURCE_GROUP_UNLOCK (group);

  if ((state_ret =
          gst_element_set_state (uridecodebin,
              GST_STATE_PAUSED)) == GST_STATE_CHANGE_FAILURE)
    goto uridecodebin_failure;

  GST_SOURCE_GROUP_LOCK (group);
  /* allow state changes of the playbin affect the group elements now */
  group_set_locked_state_unlocked (playbin, group, FALSE);
  group->active = TRUE;
  GST_SOURCE_GROUP_UNLOCK (group);

  return state_ret;

  /* ERRORS */
no_uridecodebin:
  {
    GstMessage *msg;

    GST_SOURCE_GROUP_UNLOCK (group);
    msg =
        gst_missing_element_message_new (GST_ELEMENT_CAST (playbin),
        "uridecodebin3");
    gst_element_post_message (GST_ELEMENT_CAST (playbin), msg);

    GST_ELEMENT_ERROR (playbin, CORE, MISSING_PLUGIN,
        (_("Could not create \"uridecodebin3\" element.")), (NULL));

    GST_SOURCE_GROUP_LOCK (group);

    goto error_cleanup;
  }
uridecodebin_failure:
  {
    GST_DEBUG_OBJECT (playbin, "failed state change of uridecodebin");
    GST_SOURCE_GROUP_LOCK (group);
    goto error_cleanup;
  }
sink_failure:
  {
    GST_ERROR_OBJECT (playbin, "failed to activate sinks");
    goto error_cleanup;
  }

error_cleanup:
  {
    group->selected_stream_types = 0;

    /* delete any custom sinks we might have */
    if (group->audio_sink) {
      /* If this is a automatically created sink set it to NULL */
      if (audio_sink_activated)
        gst_element_set_state (group->audio_sink, GST_STATE_NULL);
      gst_object_unref (group->audio_sink);
    }
    group->audio_sink = NULL;

    if (group->video_sink) {
      /* If this is a automatically created sink set it to NULL */
      if (video_sink_activated)
        gst_element_set_state (group->video_sink, GST_STATE_NULL);
      gst_object_unref (group->video_sink);
    }
    group->video_sink = NULL;

    if (group->text_sink) {
      /* If this is a automatically created sink set it to NULL */
      if (text_sink_activated)
        gst_element_set_state (group->text_sink, GST_STATE_NULL);
      gst_object_unref (group->text_sink);
    }
    group->text_sink = NULL;

    if (uridecodebin) {
      REMOVE_SIGNAL (group->uridecodebin, group->pad_added_id);
      REMOVE_SIGNAL (group->uridecodebin, group->pad_removed_id);
      REMOVE_SIGNAL (group->uridecodebin, group->select_stream_id);
      REMOVE_SIGNAL (group->uridecodebin, group->source_setup_id);
      REMOVE_SIGNAL (group->uridecodebin, group->about_to_finish_id);
#if 0
      REMOVE_SIGNAL (group->urisourcebin, group->autoplug_factories_id);
      REMOVE_SIGNAL (group->urisourcebin, group->autoplug_select_id);
      REMOVE_SIGNAL (group->urisourcebin, group->autoplug_continue_id);
      REMOVE_SIGNAL (group->urisourcebin, group->autoplug_query_id);
#endif

      gst_element_set_state (uridecodebin, GST_STATE_NULL);
      gst_bin_remove (GST_BIN_CAST (playbin), uridecodebin);
    }

    GST_SOURCE_GROUP_UNLOCK (group);

    return GST_STATE_CHANGE_FAILURE;
  }
}

/* must be called with PLAY_BIN_LOCK */
static gboolean
deactivate_group (GstPlayBin3 * playbin, GstSourceGroup * group)
{
  g_return_val_if_fail (group->active, FALSE);
  g_return_val_if_fail (group->valid, FALSE);

  GST_DEBUG_OBJECT (playbin, "unlinking group %p", group);

  GST_SOURCE_GROUP_LOCK (group);
  group->active = FALSE;
  group->playing = FALSE;
  group->group_id = GST_GROUP_ID_INVALID;

  group->selected_stream_types = 0;
  /* Update global selected_stream_types */
  playbin->selected_stream_types =
      playbin->groups[0].selected_stream_types | playbin->
      groups[1].selected_stream_types;
  if (playbin->active_stream_types != playbin->selected_stream_types)
    reconfigure_output (playbin);

#if 0
  /* delete any custom sinks we might have.
   * conditionally set them to null if they aren't inside playsink yet */
  if (group->audio_sink) {
    if (!gst_object_has_as_ancestor (GST_OBJECT_CAST (group->audio_sink),
            GST_OBJECT_CAST (playbin->playsink))) {
      gst_element_set_state (group->audio_sink, GST_STATE_NULL);
    }
    gst_object_unref (group->audio_sink);
  }
  group->audio_sink = NULL;
  if (group->video_sink) {
    if (!gst_object_has_as_ancestor (GST_OBJECT_CAST (group->video_sink),
            GST_OBJECT_CAST (playbin->playsink))) {
      gst_element_set_state (group->video_sink, GST_STATE_NULL);
    }
    gst_object_unref (group->video_sink);
  }
  group->video_sink = NULL;
  if (group->text_sink) {
    if (!gst_object_has_as_ancestor (GST_OBJECT_CAST (group->text_sink),
            GST_OBJECT_CAST (playbin->playsink))) {
      gst_element_set_state (group->text_sink, GST_STATE_NULL);
    }
    gst_object_unref (group->text_sink);
  }
  group->text_sink = NULL;
#endif

  if (group->uridecodebin) {
    REMOVE_SIGNAL (group->uridecodebin, group->select_stream_id);
    REMOVE_SIGNAL (group->uridecodebin, group->source_setup_id);
    REMOVE_SIGNAL (group->uridecodebin, group->about_to_finish_id);

    gst_element_set_state (group->uridecodebin, GST_STATE_NULL);
    gst_bin_remove (GST_BIN_CAST (playbin), group->uridecodebin);

    REMOVE_SIGNAL (group->uridecodebin, group->pad_added_id);
    REMOVE_SIGNAL (group->uridecodebin, group->pad_removed_id);
#if 0
    REMOVE_SIGNAL (group->urisourcebin, group->autoplug_factories_id);
    REMOVE_SIGNAL (group->urisourcebin, group->autoplug_select_id);
    REMOVE_SIGNAL (group->urisourcebin, group->autoplug_continue_id);
    REMOVE_SIGNAL (group->urisourcebin, group->autoplug_query_id);
#endif
  }

  GST_SOURCE_GROUP_UNLOCK (group);

  GST_DEBUG_OBJECT (playbin, "Done");

  return TRUE;
}

/* setup the next group to play, this assumes the next_group is valid and
 * configured. It swaps out the current_group and activates the valid
 * next_group. */
static GstStateChangeReturn
setup_next_source (GstPlayBin3 * playbin)
{
  GstSourceGroup *new_group;
  GstStateChangeReturn state_ret;

  GST_DEBUG_OBJECT (playbin, "setup next source");

  debug_groups (playbin);

  /* see if there is a next group */
  GST_PLAY_BIN3_LOCK (playbin);
  new_group = playbin->next_group;
  if (!new_group || !new_group->valid || new_group->active)
    goto no_next_group;

  /* activate the new group */
  state_ret = activate_group (playbin, new_group);
  if (state_ret == GST_STATE_CHANGE_FAILURE)
    goto activate_failed;

  GST_PLAY_BIN3_UNLOCK (playbin);

  debug_groups (playbin);

  return state_ret;

  /* ERRORS */
no_next_group:
  {
    GST_DEBUG_OBJECT (playbin, "no next group");
    GST_PLAY_BIN3_UNLOCK (playbin);
    return GST_STATE_CHANGE_FAILURE;
  }
activate_failed:
  {
    new_group->stream_changed_pending = FALSE;
    GST_DEBUG_OBJECT (playbin, "activate failed");
    new_group->valid = FALSE;
    GST_PLAY_BIN3_UNLOCK (playbin);
    return GST_STATE_CHANGE_FAILURE;
  }
}

/* The group that is currently playing is copied again to the
 * next_group so that it will start playing the next time.
 */
static gboolean
save_current_group (GstPlayBin3 * playbin)
{
  GstSourceGroup *curr_group;

  GST_DEBUG_OBJECT (playbin, "save current group");

  /* see if there is a current group */
  GST_PLAY_BIN3_LOCK (playbin);
  curr_group = playbin->curr_group;
  if (curr_group && curr_group->valid && curr_group->active) {
    /* unlink our pads with the sink */
    deactivate_group (playbin, curr_group);
  }
  /* swap old and new */
  playbin->curr_group = playbin->next_group;
  playbin->next_group = curr_group;
  GST_PLAY_BIN3_UNLOCK (playbin);

  return TRUE;
}

/* clear the locked state from all groups. This function is called before a
 * state change to NULL is performed on them. */
static gboolean
groups_set_locked_state (GstPlayBin3 * playbin, gboolean locked)
{
  GST_DEBUG_OBJECT (playbin, "setting locked state to %d on all groups",
      locked);

  GST_PLAY_BIN3_LOCK (playbin);
  GST_SOURCE_GROUP_LOCK (playbin->curr_group);
  group_set_locked_state_unlocked (playbin, playbin->curr_group, locked);
  GST_SOURCE_GROUP_UNLOCK (playbin->curr_group);
  GST_SOURCE_GROUP_LOCK (playbin->next_group);
  group_set_locked_state_unlocked (playbin, playbin->next_group, locked);
  GST_SOURCE_GROUP_UNLOCK (playbin->next_group);
  GST_PLAY_BIN3_UNLOCK (playbin);

  return TRUE;
}

static void
gst_play_bin3_check_group_status (GstPlayBin3 * playbin)
{
  if (playbin->activation_task)
    gst_task_start (playbin->activation_task);
}

static void
gst_play_bin3_activation_thread (GstPlayBin3 * playbin)
{
  GST_DEBUG_OBJECT (playbin, "starting");

  debug_groups (playbin);

  /* Check if next_group needs to be deactivated */
  GST_PLAY_BIN3_LOCK (playbin);
  if (playbin->next_group->active) {
    deactivate_group (playbin, playbin->next_group);
    playbin->next_group->valid = FALSE;
  }

  /* Is there a pending about-to-finish to be emitted ? */
  GST_SOURCE_GROUP_LOCK (playbin->curr_group);
  if (playbin->curr_group->pending_about_to_finish) {
    GST_LOG_OBJECT (playbin, "Propagating about-to-finish");
    playbin->curr_group->pending_about_to_finish = FALSE;
    GST_SOURCE_GROUP_UNLOCK (playbin->curr_group);
    /* This will activate the next source afterwards */
    emit_about_to_finish (playbin);
  } else
    GST_SOURCE_GROUP_UNLOCK (playbin->curr_group);

  GST_LOG_OBJECT (playbin, "Pausing task");
  if (playbin->activation_task)
    gst_task_pause (playbin->activation_task);
  GST_PLAY_BIN3_UNLOCK (playbin);

  GST_DEBUG_OBJECT (playbin, "done");
  return;
}

static gboolean
gst_play_bin3_start (GstPlayBin3 * playbin)
{
  GST_DEBUG_OBJECT (playbin, "starting");

  GST_PLAY_BIN3_LOCK (playbin);

  if (playbin->activation_task == NULL) {
    playbin->activation_task =
        gst_task_new ((GstTaskFunction) gst_play_bin3_activation_thread,
        playbin, NULL);
    if (playbin->activation_task == NULL)
      goto task_error;
    gst_task_set_lock (playbin->activation_task, &playbin->activation_lock);
  }
  GST_LOG_OBJECT (playbin, "clearing shutdown flag");
  g_atomic_int_set (&playbin->shutdown, 0);
  do_async_start (playbin);

  GST_PLAY_BIN3_UNLOCK (playbin);

  return TRUE;

task_error:
  {
    GST_PLAY_BIN3_UNLOCK (playbin);
    GST_ERROR_OBJECT (playbin, "Failed to create task");
    return FALSE;
  }
}

static void
gst_play_bin3_stop (GstPlayBin3 * playbin)
{
  GstTask *task;

  GST_DEBUG_OBJECT (playbin, "stopping");

  /* FIXME unlock our waiting groups */
  GST_LOG_OBJECT (playbin, "setting shutdown flag");
  g_atomic_int_set (&playbin->shutdown, 1);

  /* wait for all callbacks to end by taking the lock.
   * No dynamic (critical) new callbacks will
   * be able to happen as we set the shutdown flag. */
  GST_PLAY_BIN3_DYN_LOCK (playbin);
  GST_LOG_OBJECT (playbin, "dynamic lock taken, we can continue shutdown");
  GST_PLAY_BIN3_DYN_UNLOCK (playbin);

  /* Stop the activation task */
  GST_PLAY_BIN3_LOCK (playbin);
  if ((task = playbin->activation_task)) {
    playbin->activation_task = NULL;
    GST_PLAY_BIN3_UNLOCK (playbin);

    gst_task_stop (task);

    /* Make sure task is not running */
    g_rec_mutex_lock (&playbin->activation_lock);
    g_rec_mutex_unlock (&playbin->activation_lock);

    /* Wait for task to finish and unref it */
    gst_task_join (task);
    gst_object_unref (task);

    GST_PLAY_BIN3_LOCK (playbin);
  }
  GST_PLAY_BIN3_UNLOCK (playbin);
}

static GstStateChangeReturn
gst_play_bin3_change_state (GstElement * element, GstStateChange transition)
{
  GstStateChangeReturn ret;
  GstPlayBin3 *playbin;
  gboolean do_save = FALSE;

  playbin = GST_PLAY_BIN3 (element);

  switch (transition) {
    case GST_STATE_CHANGE_READY_TO_PAUSED:
      if (!gst_play_bin3_start (playbin))
        return GST_STATE_CHANGE_FAILURE;
      break;
    case GST_STATE_CHANGE_PAUSED_TO_READY:
    async_down:
      gst_play_bin3_stop (playbin);
      if (!do_save)
        break;
    case GST_STATE_CHANGE_READY_TO_NULL:
      /* we go async to PAUSED, so if that fails, we never make it to PAUSED
       * and we will never be called with the GST_STATE_CHANGE_PAUSED_TO_READY.
       * Make sure we do go through the same steps (see above) for
       * proper cleanup */
      if (!g_atomic_int_get (&playbin->shutdown)) {
        do_save = TRUE;
        goto async_down;
      }

      /* unlock so that all groups go to NULL */
      groups_set_locked_state (playbin, FALSE);
      break;
    default:
      break;
  }

  ret = GST_ELEMENT_CLASS (parent_class)->change_state (element, transition);
  if (ret == GST_STATE_CHANGE_FAILURE)
    goto failure;

  switch (transition) {
    case GST_STATE_CHANGE_READY_TO_PAUSED:
      if ((ret = setup_next_source (playbin)) == GST_STATE_CHANGE_FAILURE)
        goto failure;
      if (ret == GST_STATE_CHANGE_SUCCESS)
        ret = GST_STATE_CHANGE_ASYNC;

      break;
    case GST_STATE_CHANGE_PLAYING_TO_PAUSED:
      do_async_done (playbin);
      /* FIXME Release audio device when we implement that */
      break;
    case GST_STATE_CHANGE_PAUSED_TO_READY:
      save_current_group (playbin);
      break;
    case GST_STATE_CHANGE_READY_TO_NULL:
    {
      guint i;

      /* also do missed state change down to READY */
      if (do_save)
        save_current_group (playbin);
      /* Deactive the groups, set uridecodebin to NULL and unref it */
      for (i = 0; i < 2; i++) {
        if (playbin->groups[i].active && playbin->groups[i].valid) {
          deactivate_group (playbin, &playbin->groups[i]);
          playbin->groups[i].valid = FALSE;
        }

        if (playbin->groups[i].uridecodebin) {
          gst_element_set_state (playbin->groups[i].uridecodebin,
              GST_STATE_NULL);
          gst_object_unref (playbin->groups[i].uridecodebin);
          playbin->groups[i].uridecodebin = NULL;
        }

      }

      /* Set our sinks back to NULL, they might not be child of playbin */
      if (playbin->audio_sink)
        gst_element_set_state (playbin->audio_sink, GST_STATE_NULL);
      if (playbin->video_sink)
        gst_element_set_state (playbin->video_sink, GST_STATE_NULL);
      if (playbin->text_sink)
        gst_element_set_state (playbin->text_sink, GST_STATE_NULL);

      if (playbin->video_stream_combiner)
        gst_element_set_state (playbin->video_stream_combiner, GST_STATE_NULL);
      if (playbin->audio_stream_combiner)
        gst_element_set_state (playbin->audio_stream_combiner, GST_STATE_NULL);
      if (playbin->text_stream_combiner)
        gst_element_set_state (playbin->text_stream_combiner, GST_STATE_NULL);

      /* make sure the groups don't perform a state change anymore until we
       * enable them again */
      groups_set_locked_state (playbin, TRUE);
      break;
    }
    default:
      break;
  }

  if (ret == GST_STATE_CHANGE_NO_PREROLL)
    do_async_done (playbin);

  return ret;

  /* ERRORS */
failure:
  {
    do_async_done (playbin);

    if (transition == GST_STATE_CHANGE_READY_TO_PAUSED) {
      GstSourceGroup *curr_group;

      curr_group = playbin->curr_group;
      if (curr_group) {
        if (curr_group->active && curr_group->valid) {
          /* unlink our pads with the sink */
          deactivate_group (playbin, curr_group);
        }
        curr_group->valid = FALSE;
      }

      /* Swap current and next group back */
      playbin->curr_group = playbin->next_group;
      playbin->next_group = curr_group;
    }
    return ret;
  }
}

static void
gst_play_bin3_overlay_expose (GstVideoOverlay * overlay)
{
  GstPlayBin3 *playbin = GST_PLAY_BIN3 (overlay);

  gst_video_overlay_expose (GST_VIDEO_OVERLAY (playbin->playsink));
}

static void
gst_play_bin3_overlay_handle_events (GstVideoOverlay * overlay,
    gboolean handle_events)
{
  GstPlayBin3 *playbin = GST_PLAY_BIN3 (overlay);

  gst_video_overlay_handle_events (GST_VIDEO_OVERLAY (playbin->playsink),
      handle_events);
}

static void
gst_play_bin3_overlay_set_render_rectangle (GstVideoOverlay * overlay, gint x,
    gint y, gint width, gint height)
{
  GstPlayBin3 *playbin = GST_PLAY_BIN3 (overlay);

  gst_video_overlay_set_render_rectangle (GST_VIDEO_OVERLAY (playbin->playsink),
      x, y, width, height);
}

static void
gst_play_bin3_overlay_set_window_handle (GstVideoOverlay * overlay,
    guintptr handle)
{
  GstPlayBin3 *playbin = GST_PLAY_BIN3 (overlay);

  gst_video_overlay_set_window_handle (GST_VIDEO_OVERLAY (playbin->playsink),
      handle);
}

static void
gst_play_bin3_overlay_init (gpointer g_iface, gpointer g_iface_data)
{
  GstVideoOverlayInterface *iface = (GstVideoOverlayInterface *) g_iface;
  iface->expose = gst_play_bin3_overlay_expose;
  iface->handle_events = gst_play_bin3_overlay_handle_events;
  iface->set_render_rectangle = gst_play_bin3_overlay_set_render_rectangle;
  iface->set_window_handle = gst_play_bin3_overlay_set_window_handle;
}

static void
gst_play_bin3_navigation_send_event (GstNavigation * navigation,
    GstStructure * structure)
{
  GstPlayBin3 *playbin = GST_PLAY_BIN3 (navigation);

  gst_navigation_send_event (GST_NAVIGATION (playbin->playsink), structure);
}

static void
gst_play_bin3_navigation_init (gpointer g_iface, gpointer g_iface_data)
{
  GstNavigationInterface *iface = (GstNavigationInterface *) g_iface;

  iface->send_event = gst_play_bin3_navigation_send_event;
}

static const GList *
gst_play_bin3_colorbalance_list_channels (GstColorBalance * balance)
{
  GstPlayBin3 *playbin = GST_PLAY_BIN3 (balance);

  return
      gst_color_balance_list_channels (GST_COLOR_BALANCE (playbin->playsink));
}

static void
gst_play_bin3_colorbalance_set_value (GstColorBalance * balance,
    GstColorBalanceChannel * channel, gint value)
{
  GstPlayBin3 *playbin = GST_PLAY_BIN3 (balance);

  gst_color_balance_set_value (GST_COLOR_BALANCE (playbin->playsink), channel,
      value);
}

static gint
gst_play_bin3_colorbalance_get_value (GstColorBalance * balance,
    GstColorBalanceChannel * channel)
{
  GstPlayBin3 *playbin = GST_PLAY_BIN3 (balance);

  return gst_color_balance_get_value (GST_COLOR_BALANCE (playbin->playsink),
      channel);
}

static GstColorBalanceType
gst_play_bin3_colorbalance_get_balance_type (GstColorBalance * balance)
{
  GstPlayBin3 *playbin = GST_PLAY_BIN3 (balance);

  return
      gst_color_balance_get_balance_type (GST_COLOR_BALANCE
      (playbin->playsink));
}

static void
gst_play_bin3_colorbalance_init (gpointer g_iface, gpointer g_iface_data)
{
  GstColorBalanceInterface *iface = (GstColorBalanceInterface *) g_iface;

  iface->list_channels = gst_play_bin3_colorbalance_list_channels;
  iface->set_value = gst_play_bin3_colorbalance_set_value;
  iface->get_value = gst_play_bin3_colorbalance_get_value;
  iface->get_balance_type = gst_play_bin3_colorbalance_get_balance_type;
}

gboolean
gst_play_bin3_plugin_init (GstPlugin * plugin, gboolean as_playbin)
{
  GST_DEBUG_CATEGORY_INIT (gst_play_bin3_debug, "playbin3", 0, "play bin");

  if (as_playbin)
    return gst_element_register (plugin, "playbin", GST_RANK_NONE,
        GST_TYPE_PLAY_BIN);

  return gst_element_register (plugin, "playbin3", GST_RANK_NONE,
      GST_TYPE_PLAY_BIN);
}
