2015-05-10 3 views
0

Я искал много примеров использования библиотеки питона GStreamer на Windows, но только те, которые работают хорошо, как это:Play .avi видео с помощью GStreamer 1.0 и Python

#!/usr/bin/env python3 
# -*- coding:utf-8 -*- 
# GStreamer SDK Tutorials in Python 
# 
#  basic-tutorial-2 
# 
""" 
basic-tutorial-2: GStreamer concepts 
http://docs.gstreamer.com/display/GstSDK/Basic+tutorial+2%3A+GStreamer+concepts 
""" 

import sys 
from gi.repository import Gst 
Gst.init(None) 

# Create the elements 
source = Gst.ElementFactory.make("videotestsrc", "source") 
sink = Gst.ElementFactory.make("autovideosink", "sink") 

# Create the empty pipeline 
pipeline = Gst.Pipeline.new("test-pipeline") 


if not source or not sink or not pipeline: 
    print("Not all elements could be created.", file=sys.stderr) 
    exit(-1) 

# Build the pipeline 
pipeline.add(source) 
pipeline.add(sink) 
if not Gst.Element.link(source, sink): 
    print("Elements could not be linked.", file=sys.stderr) 
    exit(-1) 

# Modify the source's properties 
source.set_property("pattern", 0) 

# Start playing 
ret = pipeline.set_state(Gst.State.PLAYING) 
if ret == Gst.StateChangeReturn.FAILURE: 
    print("Unable to set the pipeline to the playing state.", file=sys.stderr) 
    exit(-1) 

# Wait until error or EOS 
bus = pipeline.get_bus() 
msg = bus.timed_pop_filtered(
    Gst.CLOCK_TIME_NONE, Gst.MessageType.ERROR | Gst.MessageType.EOS) 

# Parse message 
if (msg): 
    if msg.type == Gst.MessageType.ERROR: 
     err, debug = msg.parse_error() 
     print("Error received from element %s: %s" % (
      msg.src.get_name(), err), file=sys.stderr) 
     print("Debugging information: %s" % debug, file=sys.stderr) 
    elif msg.type == Gst.MessageType.EOS: 
     print("End-Of-Stream reached.") 
    else: 
     print("Unexpected message received.", file=sys.stderr) 

# Free resources 
pipeline.set_state(Gst.State.NULL) 

, что является простым тест и использует только «раковина объект», или те, что поток пример файла GStreamer (Синтел Movie Trailer), как это:

#!/usr/bin/env python3 
# -*- coding:utf-8 -*- 
# GStreamer SDK Tutorials in Python 
# 
#  basic-tutorial-4 
# 
""" 
basic-tutorial-4: Time management 
http://docs.gstreamer.com/display/GstSDK/Basic+tutorial+4%3A+Time+management 
""" 

import sys 
from gi.repository import Gst 
Gst.init(None) 

# Python version of GST_TIME_ARGS 


def convert_ns(t): 
    s, ns = divmod(t, 1000000000) 
    m, s = divmod(s, 60) 

    if m < 60: 
     return "0:%02i:%02i.%i" % (m, s, ns) 
    else: 
     h, m = divmod(m, 60) 
     return "%i:%02i:%02i.%i" % (h, m, s, ns) 


def handle_message(data, msg): 
    if message.type == Gst.MessageType.ERROR: 
     err, debug = message.parse_error() 
     print("Error received from element %s: %s" % (message.src.get_name(), err), file=sys.stderr) 
     print("Debugging information: %s" % debug, file=sys.stderr) 
     data["terminate"] = True 
    elif message.type == Gst.MessageType.EOS: 
     print("End-Of-Stream reached.") 
     data["terminate"] = True 
    elif message.type == Gst.MessageType.DURATION_CHANGED: 
     # The duration has changed, mark the current one as invalid 
     data["duration"] = Gst.CLOCK_TIME_NONE 
    elif message.type == Gst.MessageType.STATE_CHANGED: 
     if message.src == data["playbin"]: 
      old_state, new_state, pending_state = message.parse_state_changed() 
      print("Pipeline state changed from %s to %s." % (old_state.value_nick, new_state.value_nick)) 
      data["playing"] = (new_state == Gst.State.PLAYING) 
      if data["playing"]: 
       query = Gst.Query.new_seeking(Gst.Format.TIME) 
       if data["playbin"].query(query): 
        (aux, data["seek_enabled"], start, end) = query.parse_seeking() 
        if data["seek_enabled"]: 
         print("Seeking is ENABLED from %s to %s" % (convert_ns(start), convert_ns(end))) 
        else: 
         print("Seeking is DISABLED for this stream.") 
       else: 
        print("Seeking query failed.", file=sys.stderr) 
    else: 
     print("Unexpected message received.", file=sys.stderr) 


data = dict() 

data["playing"] = False 
data["terminate"] = False 
data["seek_enabled"] = False 
data["seek_done"] = False 
data["duration"] = Gst.CLOCK_TIME_NONE 

# Create the elements 
data["playbin"] = Gst.ElementFactory.make("playbin", "playbin") 

if not data["playbin"]: 
    print("Not all elements could be created.", file=sys.stderr) 
    exit(-1) 

# Set the URI to play 
data["playbin"].set_property(
    "uri", "http://docs.gstreamer.com/media/sintel_trailer-480p.webm") 

# Start playing 
ret = data["playbin"].set_state(Gst.State.PLAYING) 
if ret == Gst.StateChangeReturn.FAILURE: 
    print("Unable to set the pipeline to the playing state.", file=sys.stderr) 
    exit(-1) 

# Listen to the bus 
bus = data["playbin"].get_bus() 
while not data["terminate"]: 
    message = bus.timed_pop_filtered(100 * Gst.MSECOND, 
            Gst.MessageType.STATE_CHANGED | 
            Gst.MessageType.ERROR | 
            Gst.MessageType.EOS | 
            Gst.MessageType.DURATION_CHANGED) 

    # Parse message 
    if message: 
     handle_message(data, message) 
    else: 
     if data["playing"]: 
      fmt = Gst.Format.TIME 
      current = -1 
      # Query the current position of the stream 
      _, current = data['playbin'].query_position(fmt) 
      if not current: 
       print("Could not query current position", file=sys.stderr) 

      # If we didn't know it yet, query the stream duration 
      if data["duration"] == Gst.CLOCK_TIME_NONE: 
       _, data["duration"] = data['playbin'].query_duration(fmt) 
       if not data["duration"]: 
        print("Could not query current duration", file=sys.stderr) 

      print("Position %s/%s\r" % (
       convert_ns(current), convert_ns(data["duration"])), end=' ') 
      sys.stdout.flush() 

      # If seeking is enabled, we have not done it yet, and the time is 
      # right, seek 
      if data["seek_enabled"] and not data["seek_done"] and current > 10 * Gst.SECOND: 
       print("\nReached 10s, performing seek...") 
       data['playbin'].seek_simple(Gst.Format.TIME, Gst.SeekFlags.FLUSH | Gst.SeekFlags.KEY_UNIT, 30 * Gst.SECOND) 
       data["seek_done"] = True 


# Free resources 
data["playbin"].set_state(Gst.State.NULL) 

Так, после попытки изменить код у меня есть некоторые вопросы :

  1. Является ли этот файл «/// C: /folder/video.avi» правильным форматом пути для GStreamer?
  2. Я знаю, что мне нужно использовать объект «playerbin» и установить его свойство uri, но я не знаю, где именно я должен поместить эти строки и как правильно их использовать.
  3. Есть ли проблемы, вызванные видеоформатом?

Большое вам спасибо за помощь!

ответ

0
  1. выглядит правильно, но я не могу проверить это, как я использую Linux
  2. Изменить строку:
    data["playbin"].set_property( "uri", "http://docs.gstreamer.com/media/sintel_trailer-480p.webm")
    в
    data["playbin"].set_property("uri", "file:///C:/folder/video.avi")
  3. Нет, она должна быть тонкой, playbin будет работать только с о чем-то, что вы бросаете на него.
  4. http://gstreamer.freedesktop.org/data/doc/gstreamer/head/gst-plugins-base-plugins/html/gst-plugins-base-plugins-playbin.html
    , чтобы увидеть свойства playbin, которые могут быть изменены
Смежные вопросы