Re: Fixing the Gst::Message classes



Murray Cumming wrote:
On Wed, 2007-12-12 at 10:15 -0500, José Alburquerque wrote:
BTW, I was just testing the signal version of the ogg player and it seems to not be transmitting the signal.

I'm not sure what you mean here, but feel free to post a test/example
here if you'd like me to take a look.

Oops, my mistake. I re-tested, modifying the ogg player version in svn to use signals (attached as ogg-player-signal.cc) and it works. I was using the one I originally created (attached as ogg-player-signal-old.cc) and didn't get a chance to look at it, but the new modified version works fine.

-Jose

#include <gstmm.h>
#include <iostream>

Glib::RefPtr<Glib::MainLoop> mainloop;
Glib::RefPtr<Gst::Element> decoder;

void on_bus_message(const Glib::RefPtr<Gst::Message>& message)
{
  switch (message->get_message_type()) {
    case Gst::MESSAGE_EOS:
      std::cout << "End of stream" << std::endl;
      mainloop->quit();
    case Gst::MESSAGE_ERROR:
    {
      Glib::RefPtr<Gst::MessageError> msgError = Glib::RefPtr<Gst::MessageError>::cast_dynamic(message);
      if(msgError)
      {
        Glib::Error err;
        std::string debug; //TODO: Maybe this should be an optional parameter.
        msgError->parse(err, debug);
        std::cerr << "Error: " << err.what() << std::endl;
      }
      else
        std::cerr << "Error." << std::endl;

      mainloop->quit();
    }
    default:
    {
      //std::cout << "debug: on_bus_message: unhandled message=" << G_OBJECT_TYPE_NAME(message->gobj()) << std::endl;
    }
      break;
  }
}

void on_parser_pad_added(const Glib::RefPtr<Gst::Pad>& newPad)
{
  std::cout << "Dynamic pad created. Linking parser/decoder." << std::endl;
  Glib::RefPtr<Gst::Pad> sinkPad = decoder->get_pad("sink");
  newPad->link(sinkPad);
}

int main(int argc, char* argv[])
{
  if (argc != 2)
  {
    std::cout << "Usage: " << argv[0] << " <Ogg/Vorbis filename>" << std::endl;
    return -1;
  }

  Gst::init(argc, argv);
  mainloop = Glib::MainLoop::create();

  // Create elements:
  Glib::RefPtr<Gst::Pipeline> pipeline = Gst::Pipeline::create("audio-player");
  std::cout << "pipeline=" << pipeline << std::endl;
  Glib::RefPtr<Gst::Element> source = Gst::Element::create("filesrc", "file-source");
  std::cout << "source=" << source << std::endl;
  Glib::RefPtr<Gst::Element> parser = Gst::Element::create("oggdemux", "ogg-parser");
  std::cout << "parser=" << parser << std::endl;
  decoder = Gst::Element::create("vorbisdec", "vorbis-decoder");
  std::cout << "decoder=" << decoder << std::endl;
  Glib::RefPtr<Gst::Element> conv = Gst::Element::create("audioconvert", "converter");
  std::cout << "conv=" << conv << std::endl;
  Glib::RefPtr<Gst::Element> sink = Gst::Element::create("alsasink", "alsa-output");
  std::cout << "sink=" << sink << std::endl;

  if (!pipeline || !source || !parser || !decoder || !conv || !sink) {
    std::cerr << "One element could not be created" << std::endl;
    return -1;
  }

  // Set filename property on the file source. Also add a message handler:
  std::string filepath = argv[1];
  source->set_property("location", filepath);

  Glib::RefPtr<Gst::Bus> bus = pipeline->get_bus();
  bus->add_signal_watch();
  bus->signal_message().connect(sigc::ptr_fun(&on_bus_message));


  // Put all elements in a bin:
  try
  {
    pipeline->add(source)->add(parser)->add(decoder)->add(conv)->add(sink);
  }
  catch(const Glib::Error& ex)
  {
    std::cerr << "Error while adding elements to the pipeline: " << ex.what() << std::endl;
    return -1;
  }

  // Link together:
  source->link(parser);

  // We cannot link the parser and decoder yet, 
  // because the parser uses dynamic pads. For that,
  // we set a pad-added signal handler:
  parser->signal_pad_added().connect( sigc::ptr_fun(&on_parser_pad_added) );

  decoder->link(conv)->link(sink);


  // Now set to playing and iterate:
  std::cout << "Setting to PLAYING." << std::endl;
  pipeline->set_state(Gst::STATE_PLAYING);
  std::cout << "Running." << std::endl;
  mainloop->run();

  // Clean up nicely:
  std::cout << "Returned. Stopping playback." << std::endl;
  pipeline->set_state(Gst::STATE_NULL);

  return 0;
}
#include <iostream>
#include <gstmm.h>

using namespace Glib;
using namespace Gst;
using namespace std;

void bus_message_received(const RefPtr<Message>& message,
RefPtr<MainLoop> mainLoop)
{
  RefPtr<MessageError> msgError;
  Error err;
  std::string debug;

  switch (message->get_type()) {
    case MESSAGE_EOS:
      cout << "End of stream" << endl;
      mainLoop->quit();
      break;
    case MESSAGE_ERROR:
      msgError = RefPtr<MessageError>::cast_static(message);
      if (msgError) {
        msgError->parse(err, debug);
        cerr << "Error: " << err.what() << endl;
      }
      else
        cerr << "Error." << endl;
      mainLoop->quit();
      break;
    default:
      break;
  }
}

void parser_pad_added(const RefPtr<Pad>& newPad, RefPtr<Element> decoder)
{
  cout << "Dynamic pad created, linking parser/decoder." << endl;
  RefPtr<Pad> sinkPad = decoder->get_pad("sink");
  newPad->link(sinkPad);
}

int main(int argc, char* argv[]) {
  if (argc != 2) {
    cout << "Usage: " << argv[0] << " <Ogg/Vorbis filename>" << endl;
    return -1;
  }

  Gst::init(argc, argv);
  RefPtr<MainLoop> mainLoop = Glib::MainLoop::create();

  /* create elements */
  RefPtr<Pipeline> pipeline = Gst::Pipeline::create("audio-player");
  RefPtr<Element> source = Gst::Element::create("filesrc", "file-source");
  RefPtr<Element> parser = Gst::Element::create("oggdemux", "ogg-parser");
  RefPtr<Element> decoder = Gst::Element::create("vorbisdec", "vorbis-decoder");
  RefPtr<Element> conv = Gst::Element::create("audioconvert", "converter");
  RefPtr<Element> sink = Gst::Element::create("alsasink", "alsa-output");

  if (!pipeline || !source || !parser || !decoder || !conv || !sink) {
    cerr << "One element could not be created." << endl;
    return -1;
  }

  /* set filename property on the file source. Also add a message
   * handler. */
  source->set_property("location", (string) argv[1]);

  RefPtr<Bus> bus = pipeline->get_bus();
  bus->add_signal_watch();
  bus->signal_message().connect(sigc::bind< RefPtr<MainLoop> >(
    sigc::ptr_fun(&bus_message_received), mainLoop) );

  /* put all elements in a bin */
  pipeline->add(source)->add(parser)->add(decoder)->add(conv)->add(sink);

  /* link together - note that we cannot link the parser and
   * decoder yet, becuse the parser uses dynamic pads. For that,
   * we set a pad-added signal handler. */
  source->link(parser);
  decoder->link(conv)->link(sink);

  parser->signal_pad_added().connect(sigc::bind< RefPtr<Element> >(
    sigc::ptr_fun(&parser_pad_added), decoder) );

  /* Now set to playing and iterate. */
  cout << "Setting to PLAYING." << endl;
  pipeline->set_state(STATE_PLAYING);
  cout << "Running." << endl;
  mainLoop->run();

  /* clean up nicely */
  cout << "Returned, stopping playback." << endl;
  pipeline->set_state(STATE_NULL);

  bus->remove_signal_watch();

  return 0;
}


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]