/*  Copyright (C) 2015 Centricular Ltd
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 * 1. Redistributions of source code must retain the above copyright
 *    notice, this list of conditions and the following disclaimer.
 * 2. Redistributions in binary form must reproduce the above copyright
 *    notice, this list of conditions and the following disclaimer in the
 *    documentation and/or other materials provided with the distribution.
 *
 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
 * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
 * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
 * POSSIBILITY OF SUCH DAMAGE.
 */

#include <gst/gst.h>
#include <gst/video/gstvideosink.h>

#define STR_HELPER(x) #x
#define STR(x) STR_HELPER(x)

/* Change this to set the output resolution */
#define OUTPUT_VIDEO_WIDTH  1280
#define OUTPUT_VIDEO_HEIGHT 720

/* Video and audio caps outputted by the mixers */
#define RAW_AUDIO_CAPS_STR "audio/x-raw, format=(string)S16LE, " \
"layout=(string)interleaved, rate=(int)44100, channels=(int)2, " \
"channel-mask=(bitmask)0x03"

#define RAW_VIDEO_CAPS_STR "video/x-raw, width=(int)" STR(OUTPUT_VIDEO_WIDTH) \
", height=(int)" STR(OUTPUT_VIDEO_HEIGHT) ", framerate=(fraction)25/1, " \
"format=I420, pixel-aspect-ratio=(fraction)1/1, " \
"interlace-mode=(string)progressive"

GST_DEBUG_CATEGORY_STATIC (playout);
#define GST_CAT_DEFAULT playout

typedef enum
{
  PLAYOUT_APP_STATE_READY,      /* Newly created */
  PLAYOUT_APP_STATE_PLAYING,    /* Playing an item */
  PLAYOUT_APP_STATE_EOS         /* Finished playing, all items EOS */
} PlayoutAppState;

typedef struct
{
  /* Application state */
  PlayoutAppState state;

  /* An array of PlayoutItems that will be played in sequence */
  GPtrArray *play_queue;
  /* Index of the currently-playing item */
  gint play_queue_current;
  /* Lock access to the play queue */
  GMutex play_queue_lock;

  GMainLoop *main_loop;

  /* Pipeline */
  GstElement *pipeline;

  /* Output */
  GstElement *video_mixer;
  GstElement *video_sink;
  GstVideoRectangle video_orect;        /* w/h/x/y of the output */

  GstElement *audio_mixer;
  GstElement *audio_sink;

  /* The duration of all items that have been played in ns.
   * Only updates when a new item is activated. */
  guint64 elapsed_duration;
} PlayoutApp;

typedef enum
{
  PLAYOUT_ITEM_STATE_NEW,       /* Newly created */
  PLAYOUT_ITEM_STATE_PREPARED,  /* Prepared and ready to activate */
  PLAYOUT_ITEM_STATE_ACTIVATED, /* Activated */
  PLAYOUT_ITEM_STATE_FIRST_VBUFFER,     /* First video buffer has gone through */
  PLAYOUT_ITEM_STATE_AGGREGATING,       /* Audio & video buffers are aggregating */
  PLAYOUT_ITEM_STATE_EOS        /* At least one pad is EOS */
} PlayoutItemState;

typedef struct
{
  PlayoutApp *app;
  PlayoutItemState state;

  gchar *fn;

  GstElement *decoder;          /* bin with uridecodebin + converters */

  /* We just use the first audio stream and ignore the rest (if there is audio) */
  GstPad *audio_pad;            /* decoder bin audio src ghostpad */
  GstPad *video_pad;            /* decoder bin video src ghostpad */
  GstVideoRectangle video_irect;        /* input w/h/x/y of the item */
  GstVideoRectangle video_orect;        /* output w/h/x/y of the item */

  /* When this item has finished preparing and all pads have been connected to
   * mixers, the pads will be blocked till it's this item's turn to be played */
  gulong audio_pad_probe_block_id;
  gulong video_pad_probe_block_id;

  /* The current running time of this item; updated with every audio buffer if
   * this item has audio; otherwise it's updated withe very video buffer */
  guint64 running_time;
} PlayoutItem;

static PlayoutApp *playout_app_new (void);
static void playout_app_free (PlayoutApp * app);
static PlayoutItem *playout_item_new (PlayoutApp * app, const gchar * fn);
static void playout_item_free (PlayoutItem * item);

static void playout_app_add_item (PlayoutApp * app, const gchar * fn);
static gboolean playout_app_prepare_item (PlayoutItem * item);
static gboolean playout_app_activate_item (PlayoutItem * item);
static gboolean playout_app_activate_next_item (PlayoutApp * app);
static gboolean playout_app_activate_next_item_early (PlayoutApp * app);
static PlayoutItem *playout_app_get_current_item (PlayoutApp * app);
static gboolean playout_app_remove_item (PlayoutItem * item);

static void
playout_app_add_audio_sink (PlayoutApp * app)
{
  GstElement *audio_resample, *audio_conv, *queue;

  /* audiomixer doesn't do conversion yet, so we don't need an output capsfilter
   * for this branch. The output format is decided by the sink pads, which all
   * have to have the same format. */
  app->audio_mixer = gst_element_factory_make ("audiomixer", "audio_mixer");
  audio_conv = gst_element_factory_make ("audioconvert", "mixer_audioconvert");
  audio_resample = gst_element_factory_make ("audioresample",
      "audio_mixer_audioresample");
  queue = gst_element_factory_make ("queue", "asink_queue");
  app->audio_sink = gst_element_factory_make ("autoaudiosink", NULL);
  g_object_set (app->audio_sink, "async-handling", TRUE, NULL);
  gst_bin_add_many (GST_BIN (app->pipeline), app->audio_mixer, audio_conv,
      audio_resample, queue, app->audio_sink, NULL);
  gst_element_link_many (app->audio_mixer, audio_conv, audio_resample,
      queue, app->audio_sink, NULL);

  if (!gst_element_sync_state_with_parent (app->audio_mixer) ||
      !gst_element_sync_state_with_parent (audio_conv) ||
      !gst_element_sync_state_with_parent (audio_resample) ||
      !gst_element_sync_state_with_parent (queue) ||
      !gst_element_sync_state_with_parent (app->audio_sink))
    GST_ERROR ("app: unable to sync audio mixer + sink state with pipeline");
}

static PlayoutApp *
playout_app_new (void)
{
  GstElement *video_capsfilter, *queue;
  GstCaps *caps;
  PlayoutApp *app;

  app = g_new0 (PlayoutApp, 1);

  app->state = PLAYOUT_APP_STATE_READY;

  app->play_queue =
      g_ptr_array_new_with_free_func ((GDestroyNotify) playout_item_free);
  app->play_queue_current = -1;
  g_mutex_init (&app->play_queue_lock);

  app->main_loop = g_main_loop_new (NULL, FALSE);

  app->pipeline = gst_pipeline_new ("pipeline");

  /* It's best to set a caps filter for the video output format */
  app->video_orect.w = OUTPUT_VIDEO_WIDTH;
  app->video_orect.h = OUTPUT_VIDEO_HEIGHT;
  app->video_orect.x = 0;
  app->video_orect.y = 0;
  app->video_mixer = gst_element_factory_make ("compositor", "video_mixer");
  /* Set the background as black; faster while compositing, and allows us to
   * rescale videos with a different aspect ratio than the output in a way that
   * adds black borders automatically */
  g_object_set (app->video_mixer, "background", 1, NULL);
  queue = gst_element_factory_make ("queue", "vsink_queue");
  app->video_sink = gst_element_factory_make ("autovideosink", NULL);
  g_object_set (app->video_sink, "async-handling", TRUE, NULL);
  video_capsfilter = gst_element_factory_make ("capsfilter",
      "video_mixer_capsfilter");
  caps = gst_caps_from_string (RAW_VIDEO_CAPS_STR);
  g_object_set (video_capsfilter, "caps", caps, NULL);
  gst_caps_unref (caps);
  gst_bin_add_many (GST_BIN (app->pipeline), app->video_mixer, video_capsfilter,
      queue, app->video_sink, NULL);
  gst_element_link_many (app->video_mixer, video_capsfilter, queue,
      app->video_sink, NULL);

  return app;
}

static void
playout_app_free (PlayoutApp * app)
{
  GST_DEBUG ("Freeing app");
  g_ptr_array_unref (app->play_queue);
  g_main_loop_unref (app->main_loop);
  gst_element_set_state (app->pipeline, GST_STATE_NULL);
  gst_object_unref (app->pipeline);
  g_free (app);
}

static void
playout_app_eos (GstBus * bus, GstMessage * msg, PlayoutApp * app)
{
  g_print ("All streams EOS, exiting...\n");
  g_main_loop_quit (app->main_loop);
}

static PlayoutItem *
playout_item_new (PlayoutApp * app, const gchar * fn)
{
  PlayoutItem *item = g_new0 (PlayoutItem, 1);

  item->app = app;
  item->state = PLAYOUT_ITEM_STATE_NEW;
  item->fn = g_strdup (fn);

  return item;
}

/* Unlink and release the pad */
static gboolean
playout_remove_pad (GstPad * srcpad)
{
  GstPad *sinkpad;
  GstElement *mixer;

  sinkpad = gst_pad_get_peer (srcpad);
  if (!sinkpad)
    return FALSE;
  if (!gst_pad_unlink (srcpad, sinkpad))
    return FALSE;
  mixer = gst_pad_get_parent_element (sinkpad);
  gst_element_release_request_pad (mixer, sinkpad);
  GST_DEBUG ("Released some pad");

  gst_object_unref (sinkpad);
  gst_object_unref (mixer);
  return FALSE;
}

static GstPadProbeReturn
playout_item_pad_probe_blocked (GstPad * srcpad, GstPadProbeInfo * info,
    PlayoutItem * item)
{
  if (srcpad == item->audio_pad) {
    item->audio_pad_probe_block_id = GST_PAD_PROBE_INFO_ID (info);
  } else if (srcpad == item->video_pad) {
    item->video_pad_probe_block_id = GST_PAD_PROBE_INFO_ID (info);
  } else {
    g_assert_not_reached ();
  }

  return GST_PAD_PROBE_OK;
}

static GstPadProbeReturn
playout_item_pad_probe_pad_running_time (GstPad * srcpad,
    GstPadProbeInfo * info, PlayoutItem * item)
{
  GstEvent *event;
  GstBuffer *buffer;
  guint64 running_time;
  const GstSegment *segment;

  buffer = GST_PAD_PROBE_INFO_BUFFER (info);
  event = gst_pad_get_sticky_event (srcpad, GST_EVENT_SEGMENT, 0);
  GST_TRACE ("%s: pad sticky event: %" GST_PTR_FORMAT, item->fn, event);

  if (event) {
    gst_event_parse_segment (event, &segment);
    gst_event_unref (event);
    running_time = gst_segment_to_running_time (segment, GST_FORMAT_TIME,
        GST_BUFFER_PTS (buffer));
  } else {
    GST_WARNING ("%s: unable to parse event for segment; falling back to pts. "
        "Output will probably have glitches.", item->fn);
    running_time = GST_BUFFER_PTS (buffer);
  }

  item->running_time = running_time + GST_BUFFER_DURATION (buffer);
  GST_TRACE ("%s: running time is %" G_GUINT64_FORMAT ", duration is %"
      G_GUINT64_FORMAT, item->fn, item->running_time,
      GST_BUFFER_DURATION (buffer));

  return GST_PAD_PROBE_PASS;
}

static GstPadProbeReturn
playout_item_pad_probe_video_pad_eos_on_buffer (GstPad * srcpad,
    GstPadProbeInfo * info, PlayoutItem * prev_item)
{
  PlayoutItem *current_item;

  current_item = playout_app_get_current_item (prev_item->app);

  if (!current_item)
    return GST_PAD_PROBE_REMOVE;

  /* Step through the item's states as buffers pass through. The first buffer
   * will be taken by the video_mixer, and kept till the audio running time
   * matches the video buffer running time. When the second buffer gets through,
   * we know that this pad has begun aggregating. */
  switch (current_item->state) {
    case PLAYOUT_ITEM_STATE_NEW:
    case PLAYOUT_ITEM_STATE_PREPARED:
      GST_DEBUG ("%s: new/prepared", current_item->fn);
      break;
    case PLAYOUT_ITEM_STATE_ACTIVATED:
      GST_DEBUG ("%s: activated -> first vbuffer", current_item->fn);
      current_item->state = PLAYOUT_ITEM_STATE_FIRST_VBUFFER;
      break;
    case PLAYOUT_ITEM_STATE_FIRST_VBUFFER:
      GST_DEBUG ("%s: first vbuffer -> aggregating", current_item->fn);
      current_item->state = PLAYOUT_ITEM_STATE_AGGREGATING;
      gst_pad_remove_probe (srcpad, GST_PAD_PROBE_INFO_ID (info));
      /* Item is aggregating, release the previous item's video pad */
      goto release;
      break;
    case PLAYOUT_ITEM_STATE_EOS:
      return GST_PAD_PROBE_REMOVE;
    default:
      g_assert_not_reached ();
  }

  return GST_PAD_PROBE_PASS;

release:
  {
    playout_remove_pad (prev_item->video_pad);
    GST_DEBUG ("%s: released video pad", prev_item->fn);
    prev_item->video_pad = NULL;

    /* If there's no audio pad, or if the audio pad is already EOS, we can
     * remove this item from the queue which will free it. Need to free the
     * item from the main thread because it causes the item's decoder bin
     * to be removed from the pipeline, which cannot be done in the
     * streaming thread */
    if (prev_item->audio_pad == NULL) {
      GST_DEBUG ("%s: queued item removal (last pad is video)", prev_item->fn);
      g_main_context_invoke (NULL, (GSourceFunc) playout_app_remove_item,
          prev_item);
    }

    /* Pad probe has already been removed above */
    return GST_PAD_PROBE_PASS;
  }
}

/* This is called on EOS for both item->audio_pad and item->video_pad
 *
 * FIXME: Add locking. Both pads could go EOS at the exact same time. */
static GstPadProbeReturn
playout_item_pad_probe_event (GstPad * srcpad, GstPadProbeInfo * info,
    PlayoutItem * item)
{
  GstEventType type;
  gboolean ret = TRUE;
  GstPadProbeReturn probe_ret = GST_PAD_PROBE_DROP;

  type = GST_EVENT_TYPE (GST_PAD_PROBE_INFO_DATA (info));
  if (type != GST_EVENT_EOS)
    return GST_PAD_PROBE_PASS;

  /* We might get two EOSes on this pad if we send an artificial EOS. Remove
   * the probe so this is only called once for each pad */
  gst_pad_remove_probe (srcpad, GST_PAD_PROBE_INFO_ID (info));

  GST_DEBUG ("%s: recvd some EOS", item->fn);

  if (item->state != PLAYOUT_ITEM_STATE_EOS) {
    /* We have more than one pad per item (video + audio item), and this is the
     * first pad to go EOS or we have only one pad per item, and that pad has
     * gone EOS. For the first case, the other pad might still have some buffers
     * to output before going EOS, but we need to activate the next item and
     * start outputting buffers from that immediately. */

    /* Update the total elapsed duration from the item's current running time */
    item->app->elapsed_duration += item->running_time;

    GST_DEBUG ("%s: activating next item", item->fn);
    /* Activate the next item if and only if this is the first pad to go EOS */
    ret = playout_app_activate_next_item (item->app);
    if (!ret) {
      GST_DEBUG ("%s: App is going EOS", item->fn);
      item->state = PLAYOUT_ITEM_STATE_EOS;
      item->app->state = PLAYOUT_APP_STATE_EOS;
      /* If we couldn't activate the next item, pass the EOS event onward,
       * ending the stream */
      probe_ret = GST_PAD_PROBE_PASS;
    }
  }

  g_assert (srcpad != NULL);

  if (srcpad == item->audio_pad) {
    GST_DEBUG ("%s: audio pad was EOS", item->fn);

    if (item->app->state != PLAYOUT_APP_STATE_EOS) {
      /* While activating the next item, we ensure that there's no offset mismatch
       * which would cause audiomixer to output silence, so we can release the
       * previous item's audio request pad here. We also unlink the audio pad;
       * nothing else is needed from it */
      playout_remove_pad (srcpad);
      GST_DEBUG ("%s: released audio pad", item->fn);

      /* If there's no video pad, or if the video pad is already EOS, we can
       * remove this item from the queue which will free it. Need to free the
       * item from the main thread because it causes the item's decoder bin
       * to be removed from the pipeline, which cannot be done in the
       * streaming thread */
      if (item->video_pad == NULL) {
        GST_DEBUG ("%s: queued item removal (last pad is audio)", item->fn);
        g_main_context_invoke (NULL, (GSourceFunc) playout_app_remove_item,
            item);
      }
    } else {
      /* If this is the last pad on audio_mixer, let the EOS go through
       * before unlinking/releasing the pad. This should happen within 500ms. */
      g_timeout_add (500, (GSourceFunc) playout_remove_pad, srcpad);
      GST_DEBUG ("%s: queued audio pad release", item->fn);

      if (item->video_pad == NULL) {
        /* Unlike above, we need to wait till the pad is removed before removing
         * the item from the app, so we queue it for 100ms afterwards */
        GST_DEBUG ("%s: queued last item removal (last pad is audio)",
            item->fn);
        g_timeout_add (600, (GSourceFunc) playout_app_remove_item, item);
      }
    }
    item->audio_pad = NULL;
  } else if (srcpad == item->video_pad) {

    GST_DEBUG ("%s: video pad was EOS", item->fn);

    if (item->audio_pad != NULL)
      GST_WARNING ("%s: video pad went EOS before audio pad! "
          "There will be audio/video glitches while switching.", item->fn);

    if (item->app->state != PLAYOUT_APP_STATE_EOS) {
      PlayoutItem *next_item;

      next_item = playout_app_get_current_item (item->app);
      GST_DEBUG ("%s: next item is %s, %i/%i", item->fn, next_item->fn,
          next_item->state, PLAYOUT_ITEM_STATE_ACTIVATED);

      g_assert (next_item != NULL);
      /* If there's another item being activated, release this video pad only
       * when the next item's video pad starts being aggregated; that happens
       * when this probe receives its 2nd buffer from the next item */
      gst_pad_add_probe (next_item->video_pad, GST_PAD_PROBE_TYPE_BUFFER,
          (GstPadProbeCallback) playout_item_pad_probe_video_pad_eos_on_buffer,
          item, NULL);
    } else {
      /* If this is the last pad on video_mixer, let the EOS go through
       * before unlinking/releasing the pad. This should happen within 500ms. */
      g_timeout_add (500, (GSourceFunc) playout_remove_pad, srcpad);
      GST_DEBUG ("%s: queued video pad release", item->fn);
      item->video_pad = NULL;
    }
    probe_ret = GST_PAD_PROBE_PASS;
  } else {
    g_assert_not_reached ();
  }

  item->state = PLAYOUT_ITEM_STATE_EOS;

  /* NOTE: If the srcpad has been unlinked, the return value is useless */
  return probe_ret;
}

/* On the "pad-added" signal of uridecodebin, add converters and connect to
 * audio/video mixers */
static void
playout_item_new_pad (GstElement * uridecodebin, GstPad * pad,
    PlayoutItem * item)
{
  GstStructure *s;
  GstCaps *caps;
  GstPad *sinkpad, *srcpad;
  GstElement *queue;
  GstPadProbeType block_probe_type;

  caps = gst_pad_get_current_caps (pad);
  s = gst_caps_get_structure (caps, 0);
  GST_DEBUG ("%s: new pad: %p, caps: %s", item->fn, pad,
      gst_structure_get_name (s));

  if (gst_structure_has_name (s, "audio/x-raw")) {
    if (item->audio_pad != NULL)
      /* Ignore all audio pads after the first one */
      goto out;
    goto audio;
  } else if (gst_structure_has_name (s, "video/x-raw")) {
    if (item->video_pad != NULL)
      /* Ignore all video pads after the first one */
      goto out;
    goto video;
  } else {
    goto out;
  }

audio:
  {
    GstCaps *wanted_caps;
    GstElement *audioconvert, *audioresample, *capsfilter;

    /* Audio pad found; add audio mixer and audio sink to the pipeline.
     * NOTE: If any items after this do not have an audio pad, the pipeline will
     * mess up because the audio sink will not receive any data. */
    if (item->app->audio_sink == NULL)
      playout_app_add_audio_sink (item->app);

    wanted_caps = gst_caps_from_string (RAW_AUDIO_CAPS_STR);

    if (!gst_caps_is_equal (caps, wanted_caps)) {
      GST_DEBUG ("%s: converting audio caps", item->fn);
      /* We need to convert the audio to the wanted format because
       * audiomixer doesn't do format conversion */
      audioresample = gst_element_factory_make ("audioresample", NULL);
      audioconvert = gst_element_factory_make ("audioconvert", NULL);
      capsfilter = gst_element_factory_make ("capsfilter", NULL);
      g_object_set (capsfilter, "caps", wanted_caps, NULL);
      queue = gst_element_factory_make ("queue", NULL);
      gst_bin_add_many (GST_BIN (item->decoder), audioresample, audioconvert,
          capsfilter, queue, NULL);

      sinkpad = gst_element_get_static_pad (audioresample, "sink");
      gst_pad_link (pad, sinkpad);
      gst_object_unref (sinkpad);
      gst_element_link_many (audioresample, audioconvert, capsfilter, queue,
          NULL);
      srcpad = gst_element_get_static_pad (queue, "src");

      if (!gst_element_sync_state_with_parent (audioresample) ||
          !gst_element_sync_state_with_parent (audioconvert) ||
          !gst_element_sync_state_with_parent (capsfilter) ||
          !gst_element_sync_state_with_parent (queue)) {
        GST_ERROR ("%s: unable to sync audio converter state with decoder",
            item->fn);
        goto out;
      }
    } else {
      queue = gst_element_factory_make ("queue", NULL);
      gst_bin_add (GST_BIN (item->decoder), queue);
      sinkpad = gst_element_get_static_pad (queue, "sink");
      gst_pad_link (pad, sinkpad);
      gst_object_unref (sinkpad);

      srcpad = gst_element_get_static_pad (queue, "src");

      if (!gst_element_sync_state_with_parent (queue)) {
        GST_ERROR ("%s: unable to sync audio queue state with decoder",
            item->fn);
        goto out;
      }
    }
    gst_caps_unref (wanted_caps);

    /* Convert the audioconvert src pad to a ghostpad on the bin */
    item->audio_pad = gst_ghost_pad_new (NULL, srcpad);
    gst_pad_set_active (item->audio_pad, TRUE);
    gst_element_add_pad (item->decoder, item->audio_pad);
    gst_object_unref (srcpad);

    srcpad = item->audio_pad;
    GST_DEBUG ("%s: created audio pad", item->fn);
    goto done;
  }

video:
  {
    if (!gst_structure_get_int (s, "width", &item->video_irect.w) ||
        !gst_structure_get_int (s, "height", &item->video_irect.h))
      GST_WARNING ("%s: unable to set width/height from caps", item->fn);
    item->video_irect.x = item->video_irect.y = 0;

    queue = gst_element_factory_make ("queue", "video-decoder-queue-%u");
    gst_bin_add (GST_BIN (item->decoder), queue);

    if (!gst_element_sync_state_with_parent (queue)) {
      GST_ERROR ("%s: unable to sync video queue state with decoder", item->fn);
      goto out;
    }

    sinkpad = gst_element_get_static_pad (queue, "sink");
    gst_pad_link (pad, sinkpad);
    gst_object_unref (sinkpad);

    /* Convert the queue src pad to a ghostpad on the bin */
    srcpad = gst_element_get_static_pad (queue, "src");
    item->video_pad = gst_ghost_pad_new (NULL, srcpad);
    gst_pad_set_active (item->video_pad, TRUE);
    gst_element_add_pad (item->decoder, item->video_pad);
    gst_object_unref (srcpad);

    srcpad = item->video_pad;
    GST_DEBUG ("%s: created video pad", item->fn);
    goto done;
  }

done:
  /* We let events and queries through */
  block_probe_type = GST_PAD_PROBE_TYPE_BLOCK |
      GST_PAD_PROBE_TYPE_BUFFER | GST_PAD_PROBE_TYPE_BUFFER_LIST;
  /* If the app is already playing an item, block everything except queries
   * till we need to play this item */
  if (item->app->state != PLAYOUT_APP_STATE_READY)
    gst_pad_add_probe (srcpad, block_probe_type,
        (GstPadProbeCallback) playout_item_pad_probe_blocked, item, NULL);
  /* Probe events for EOS */
  gst_pad_add_probe (srcpad, GST_PAD_PROBE_TYPE_EVENT_DOWNSTREAM,
      (GstPadProbeCallback) playout_item_pad_probe_event, item, NULL);

out:
  gst_caps_unref (caps);
}

/* All pads on uridecodebin have finished being populated; the item has been
 * prepared and is ready to be activated */
static void
playout_item_no_more_pads (GstElement * uridecodebin, PlayoutItem * item)
{
  /* Set a buffer pad probe that constantly updates the item's
   * elapsed_duration using the duration of each audio buffer */
  if (item->audio_pad) {
    gst_pad_add_probe (item->audio_pad, GST_PAD_PROBE_TYPE_BUFFER,
        (GstPadProbeCallback) playout_item_pad_probe_pad_running_time,
        item, NULL);
  } else if (item->video_pad) {
    gst_pad_add_probe (item->video_pad, GST_PAD_PROBE_TYPE_BUFFER,
        (GstPadProbeCallback) playout_item_pad_probe_pad_running_time,
        item, NULL);
  } else {
    GST_ERROR ("%s: no pads were generated! Can't continue playing!", item->fn);
    return;
  }

  item->state = PLAYOUT_ITEM_STATE_PREPARED;
  GST_DEBUG ("%s: prepared", item->fn);

  if (item->app->state != PLAYOUT_APP_STATE_READY)
    /* This item will be activated when the previous one is EOS */
    return;

  GST_DEBUG ("Application isn't already playing; activate the item and prepare"
      " the next one");

  playout_app_activate_item (item);
  item->state = PLAYOUT_ITEM_STATE_ACTIVATED;
  item->app->state = PLAYOUT_APP_STATE_PLAYING;

  if (item->app->play_queue->len > 1)
    playout_app_prepare_item (g_ptr_array_index (item->app->play_queue, 1));
}

static GstElement *
playout_item_create_decoder (PlayoutItem * item)
{
  GstElement *bin, *dec;
  GError *err = NULL;
  gchar *uri;

  uri = gst_filename_to_uri (item->fn, &err);
  if (err != NULL) {
    GST_WARNING ("Could not convert '%s' to uri: %s", item->fn, err->message);
    g_clear_error (&err);
    return NULL;
  }

  bin = gst_bin_new (NULL);
  dec = gst_element_factory_make ("uridecodebin", NULL);
  g_object_set (dec, "uri", uri, NULL);
  g_free (uri);

  gst_bin_add (GST_BIN (bin), dec);

  g_signal_connect (dec, "pad-added", G_CALLBACK (playout_item_new_pad), item);
  g_signal_connect (dec, "no-more-pads", G_CALLBACK (playout_item_no_more_pads),
      item);

  return bin;
}

static void
playout_item_free (PlayoutItem * item)
{
  GST_DEBUG ("Entering free");
  switch (gst_element_set_state (item->decoder, GST_STATE_NULL)) {
    case GST_STATE_CHANGE_FAILURE:
      GST_ERROR ("%s: Unable to change state to NULL", item->fn);
      break;
    case GST_STATE_CHANGE_SUCCESS:
      GST_DEBUG ("%s: State change success", item->fn);
      break;
    default:
      GST_DEBUG ("%s: Some async/no-preroll", item->fn);
  }

  gst_bin_remove (GST_BIN (item->app->pipeline), item->decoder);
  GST_DEBUG ("%s: bin removed", item->fn);

  g_free (item->fn);
  g_free (item);
  GST_DEBUG ("item freed");
}

static guint64
playout_item_pad_get_segment_time (GstPad * srcpad)
{
  GstEvent *event;
  const GstSegment *segment;

  event = gst_pad_get_sticky_event (srcpad, GST_EVENT_SEGMENT, 0);
  if (!event)
    return 0;
  gst_event_parse_segment (event, &segment);
  gst_event_unref (event);
  return segment->time;
}

static void
playout_app_add_item (PlayoutApp * app, const gchar * fn)
{
  PlayoutItem *item;

  item = playout_item_new (app, fn);

  g_mutex_lock (&app->play_queue_lock);
  g_ptr_array_add (app->play_queue, item);
  g_mutex_unlock (&app->play_queue_lock);
}

static gboolean
playout_app_remove_item (PlayoutItem * item)
{
  PlayoutApp *app;
  GST_DEBUG ("%s: removing and freeing", item->fn);

  app = item->app;

  g_mutex_lock (&app->play_queue_lock);
  g_ptr_array_remove (app->play_queue, item);
  if (item->state >= PLAYOUT_ITEM_STATE_ACTIVATED)
    /* Removed item was playing; decrement the current-play-queue index */
    app->play_queue_current--;
  g_mutex_unlock (&app->play_queue_lock);

  /* Don't call this again */
  return FALSE;
}

static PlayoutItem *
playout_app_get_current_item (PlayoutApp * app)
{
  if (app->play_queue_current < 0 ||
      app->play_queue->len < (app->play_queue_current + 1))
    return NULL;

  return g_ptr_array_index (app->play_queue, app->play_queue_current);
}

static gboolean
playout_app_prepare_item (PlayoutItem * item)
{
  PlayoutApp *app = item->app;

  if (item->decoder != NULL)
    return TRUE;

  item->decoder = playout_item_create_decoder (item);

  if (item->decoder == NULL)
    return FALSE;

  gst_bin_add (GST_BIN (app->pipeline), item->decoder);

  if (!gst_element_sync_state_with_parent (item->decoder)) {
    GST_ERROR ("%s: unable to sync state with parent", item->fn);
    return FALSE;
  }

  GST_DEBUG ("%s: preparing", item->fn);

  /* All further processing is done in the "no-more-pads" callback of
   * uridecodebin */
  return TRUE;
}

/* Called exactly once for each item */
static gboolean
playout_app_activate_item (PlayoutItem * item)
{
  GstPad *sinkpad;
  guint64 segment_time;
  PlayoutApp *app = item->app;

  if (item->state != PLAYOUT_ITEM_STATE_PREPARED) {
    GST_ERROR ("Item %s is not ready to be activated!", item->fn);
    return FALSE;
  }

  if (!item->audio_pad && !item->video_pad) {
    GST_ERROR ("Item %s has no pads! Can't activate it!", item->fn);
    return FALSE;
  }

  /* Hook up to mixers and remove the probes blocking the pads */
  if (item->audio_pad) {
    GST_DEBUG ("%s: hooking up audio pad to mixer", item->fn);
    sinkpad = gst_element_get_request_pad (app->audio_mixer, "sink_%u");
    gst_pad_link (item->audio_pad, sinkpad);

    segment_time = playout_item_pad_get_segment_time (item->audio_pad);
    if (segment_time > 0) {
      /* If the segment time is > 0, the new pad wants audiomixer to output audio
       * silence for that duration. This will cause audio glitches, so we  move
       * the pad offset back by that amount and tell audiomixer to start mixing
       * our buffers immediately. */
      GST_DEBUG ("%s: subtracting segment time %" G_GUINT64_FORMAT " from "
          "elapsed duration before setting it as the pad offset", item->fn,
          segment_time);
      if (app->elapsed_duration > segment_time)
        app->elapsed_duration -= segment_time;
      else
        app->elapsed_duration = 0;
    }

    if (app->elapsed_duration > 0) {
      GST_DEBUG ("%s: set audio pad offset to %" G_GUINT64_FORMAT "ms",
          item->fn, app->elapsed_duration / GST_MSECOND);
      gst_pad_set_offset (item->audio_pad, app->elapsed_duration);
    }

    if (item->audio_pad_probe_block_id > 0) {
      GST_DEBUG ("%s: removing audio pad block probe", item->fn);
      gst_pad_remove_probe (item->audio_pad, item->audio_pad_probe_block_id);
    }
    gst_object_unref (sinkpad);
  }

  if (item->video_pad) {
    GST_DEBUG ("%s: hooking up video pad to mixer", item->fn);
    sinkpad = gst_element_get_request_pad (app->video_mixer, "sink_%u");

    /* Get new height/width/xpos/ypos such that the video scales up or down to
     * fit within the output video size without any cropping */
    gst_video_sink_center_rect (item->video_irect, item->app->video_orect,
        &item->video_orect, TRUE);
    GST_DEBUG ("%s: w: %i, h: %i, x: %i, y: %i\n", item->fn,
        item->video_orect.w, item->video_orect.h, item->video_orect.x,
        item->video_orect.y);
    g_object_set (sinkpad, "width", item->video_orect.w, "height",
        item->video_orect.h, "xpos", item->video_orect.x, "ypos",
        item->video_orect.y, NULL);

    /* If this is not the last item, on EOS, continue to aggregate using the
     * last buffer till the pad is released */
    if (item->app->play_queue->len != (item->app->play_queue_current + 2))
      g_object_set (sinkpad, "ignore-eos", TRUE, NULL);
    else
      GST_DEBUG ("%s: last item, not setting ignore-eos", item->fn);
    gst_pad_link (item->video_pad, sinkpad);

    if (app->elapsed_duration > 0) {
      GST_DEBUG ("%s: set video pad offset to %" G_GUINT64_FORMAT "ms",
          item->fn, app->elapsed_duration / GST_MSECOND);
      gst_pad_set_offset (item->video_pad, app->elapsed_duration);
    }

    if (item->video_pad_probe_block_id > 0) {
      GST_DEBUG ("%s: removing video pad block probe", item->fn);
      gst_pad_remove_probe (item->video_pad, item->video_pad_probe_block_id);
    }
    gst_object_unref (sinkpad);
  }

  item->state = PLAYOUT_ITEM_STATE_ACTIVATED;
  g_mutex_lock (&item->app->play_queue_lock);
  item->app->play_queue_current++;
  g_mutex_unlock (&item->app->play_queue_lock);

  GST_DEBUG ("%s: activated", item->fn);

  return TRUE;
}

/* Activate the next item, and prepare the one after that for later activation */
static gboolean
playout_app_activate_next_item (PlayoutApp * app)
{
  PlayoutItem *item;
  gboolean ret;

  if (app->play_queue->len < (app->play_queue_current + 2)) {
    g_print ("No more items to play\n");
    return FALSE;
  }

  item = g_ptr_array_index (app->play_queue, app->play_queue_current + 1);
  ret = playout_app_activate_item (item);
  if (!ret) {
    /* Tell caller, who can then decide whether to skip or error out */
    GST_ERROR ("%s: unable to activate", item->fn);
    return FALSE;
  }
  if (app->play_queue->len > (app->play_queue_current + 1)) {
    item = g_ptr_array_index (app->play_queue, app->play_queue_current + 1);
    /* FIXME: What if this fails? Prepare the next one in the queue? */
    ret = playout_app_prepare_item (item);
    if (!ret)
      GST_ERROR ("%s: unable to prepare", item->fn);
  }
  return ret;
}

static GstPadProbeReturn
playout_item_pad_probe_video_pad_running_time (GstPad * srcpad,
    GstPadProbeInfo * info, PlayoutItem * item)
{
  GstEvent *event;
  GstBuffer *buffer;
  guint64 running_time;
  const GstSegment *segment;

  buffer = GST_PAD_PROBE_INFO_BUFFER (info);
  event = gst_pad_get_sticky_event (srcpad, GST_EVENT_SEGMENT, 0);
  GST_TRACE ("%s: video sticky event: %" GST_PTR_FORMAT, item->fn, event);

  if (event) {
    gst_event_parse_segment (event, &segment);
    gst_event_unref (event);
    running_time = gst_segment_to_running_time (segment, GST_FORMAT_TIME,
        GST_BUFFER_PTS (buffer));
  } else {
    GST_WARNING ("%s: unable to parse video event for segment; falling back to "
        "pts", item->fn);
    running_time = GST_BUFFER_PTS (buffer);
  }

  if (running_time >= item->running_time) {
    /* The video buffer passing through video_mixer now matches the audio buffer
     * that passed through audio_mixer when the early switch was requested, so
     * this is the time to send an EOS to video_pad, which will complete the
     * switch */
    GST_DEBUG ("Sending video EOS to %s", item->fn);
    gst_pad_push_event (item->video_pad, gst_event_new_eos ());
    return GST_PAD_PROBE_DROP;
  } else {
    return GST_PAD_PROBE_PASS;
  }
}

static gboolean
playout_app_activate_next_item_early (PlayoutApp * app)
{
  PlayoutItem *item;

  item = playout_app_get_current_item (app);
  if (!item) {
    GST_WARNING ("Unable to switch early, no current item");
    return FALSE;
  }

  if (item->audio_pad) {
    /* If we have an audio pad, EOS audio first, always */
    GST_DEBUG ("Sending audio EOS to %s", item->fn);
    gst_pad_push_event (item->audio_pad, gst_event_new_eos ());
    /* We can't send the EOS to the video_pad yet because the running times for
     * both mixers are different due to buffering at the audio sink. So we wait
     * till the running time of the video_pad matches that of the audio_pad at
     * the time the audio EOS was sent, and then EOS video as well. */
    gst_pad_add_probe (item->video_pad, GST_PAD_PROBE_TYPE_BUFFER,
        (GstPadProbeCallback) playout_item_pad_probe_video_pad_running_time,
        item, NULL);
  } else if (item->video_pad) {
    /* If we have a video pad, EOS audio first, always */
    GST_DEBUG ("Sending video EOS to %s", item->fn);
    gst_pad_push_event (item->video_pad, gst_event_new_eos ());
  } else {
    g_assert_not_reached ();
  }

  /* Return FALSE so this function is called only once */
  return FALSE;
}

static gboolean
playout_app_play (PlayoutApp * app)
{
  PlayoutItem *item;

  item = app->play_queue->len ? g_ptr_array_index (app->play_queue, 0) : NULL;
  if (!item) {
    g_printerr ("Nothing to play\n");
    return FALSE;
  }

  playout_app_prepare_item (item);
  return TRUE;
}

/*
 * playout: An example application to sequentially and seamlessly play a list of
 * audio-video or video-only files.
 *
 * This example application uses the compositor and audiomixer elements combined
 * with pad probes to stitch together a list of A/V or V-only files in such
 * a way that audio and video glitching is minimised. Mixing A/V and V-only
 * files is not supported because it complicates the architecture quite a bit.
 *
 * Due to the fundamental difference in the representation of audio and video
 * data, unless constructed specifically for the purpose of being stitched back,
 * the audio and video tracks of files will rarely end at the same PTS. There is
 * usually a sync difference of a few frames. This application tries to stitch
 * together the audio tracks as perfectly as possible, and duplicates/drops
 * video frames if there is an underrun/overrun. Even when audio samples are
 * played back-to-back, there might be glitches due to quirks in the decoder.
 *
 * The list of PlayoutItems can be edited and added to dynamically; except the
 * currently-playing item and the next one (which has been prepared already).
 */
int
main (int argc, char **argv)
{
  GstBus *bus;
  gint switch_after_ms = 0;
  gchar **f, **filenames = NULL;
  GOptionEntry options[] = {
    {"switch-after", 's', 0, G_OPTION_ARG_INT, &switch_after_ms, "Time after "
          "which the next file will be forcibly activated", "MILLISECONDS"},
    {G_OPTION_REMAINING, 0, 0, G_OPTION_ARG_FILENAME_ARRAY, &filenames, NULL,
        "FILENAME1 [FILENAME2] [FILENAME3] ..."},
    {NULL}
  };
  GOptionContext *ctx;
  PlayoutApp *app;
  GError *err = NULL;

  ctx = g_option_context_new (NULL);
  g_option_context_set_summary (ctx, "An example application to sequentially "
      "and seamlessly play a list of audio-video or video-only files.");
  g_option_context_add_main_entries (ctx, options, NULL);
  g_option_context_add_group (ctx, gst_init_get_option_group ());

  if (!g_option_context_parse (ctx, &argc, &argv, &err)) {
    if (err)
      g_printerr ("Error initializing: %s\n", err->message);
    else
      g_printerr ("Error initializing: Unknown error!\n");
    g_option_context_free (ctx);
    g_clear_error (&err);
    return 1;
  }

  if (filenames == NULL || *filenames == NULL) {
    g_printerr ("%s", g_option_context_get_help (ctx, TRUE, NULL));
    return 1;
  }

  g_option_context_free (ctx);

  GST_DEBUG_CATEGORY_INIT (playout, "playout", 0, "Playout example app");

  app = playout_app_new ();

  for (f = filenames; f != NULL && *f != NULL; ++f)
    playout_app_add_item (app, *f);

  g_strfreev (filenames);

  if (!playout_app_play (app))
    return 1;

  GST_DEBUG ("Setting pipeline to PLAYING");

  bus = gst_pipeline_get_bus (GST_PIPELINE (app->pipeline));
  gst_bus_add_signal_watch (bus);
  g_signal_connect (bus, "message::eos", G_CALLBACK (playout_app_eos), app);
  gst_object_unref (bus);

  gst_element_set_state (app->pipeline, GST_STATE_PLAYING);

  if (switch_after_ms)
    g_timeout_add (switch_after_ms,
        (GSourceFunc) playout_app_activate_next_item_early, app);

  GST_DEBUG ("Running mainloop");
  g_main_loop_run (app->main_loop);

  playout_app_free (app);

  return 0;
}
