def __message(self, bus, message): if message.type == gst.MESSAGE_EOS: self.next(force_advance=False) elif message.type == gst.MESSAGE_TAG: self.__parse_tags(message.parse_tag()) elif message.type == gst.MESSAGE_BUFFERING: # TODO: Emit "buffering" message for the statusbar to listen for. # We can't import from blastatusbar on module level as it'd create # circular imports. global BlaStatusbar if BlaStatusbar is None: from blaplay.blagui.blastatusbar import BlaStatusbar percentage = message.parse_buffering() s = "Buffering: %d %%" % percentage BlaStatusbar.set_view_info(blaconst.VIEW_RADIO, s) if percentage == 0: print_d("Start buffering...") elif percentage == 100: self.__bin.set_state(gst.STATE_PLAYING) self.__state = blaconst.STATE_PLAYING self.emit("track_changed") self.emit("state_changed") gobject.timeout_add( 2000, BlaStatusbar.set_view_info, blaconst.VIEW_RADIO, "") print_d("Finished buffering") elif message.type == gst.MESSAGE_ERROR: self.stop() err, debug = message.parse_error() from blaplay.blagui import blaguiutils blaguiutils.error_dialog("Error", str(err))
def play(self): if not self.__uri: if blacfg.getint("general", "view") == blaconst.VIEW_RADIO: args = ("get_station", blaconst.TRACK_PLAY) else: args = ("get_track", blaconst.TRACK_PLAY, True) return self.emit(*args) # Check if the resource is available. If it's not it's best to stop # trying and inform the user about the situation. If we'd just ask # for another track we'd potentially end up hitting the interpreter's # recursion limit in case lots of tracks turn out to be invalid. if not os.path.exists(self.__uri) or not os.path.isfile(self.__uri): from blaplay.blagui import blaguiutils uri = self.__uri self.stop() blaguiutils.error_dialog("Playback error", "Resource \"%s\" unavailable." % uri) return # If `update_track' returns None it means the track needed updating, # but failed to be parsed properly so request another song. if library.update_track(self.__uri) is None: self.emit("get_track", blaconst.TRACK_PLAY, True) if (self.__state == blaconst.STATE_STOPPED and not self.__init_pipeline()): return self.__bin.set_state(gst.STATE_NULL) self.__bin.set_property("uri", "file://%s" % self.__uri) self.__bin.set_state(gst.STATE_PLAYING) self.__station = None self.__state = blaconst.STATE_PLAYING self.emit("track_changed") self.emit("state_changed")
def __init_pipeline(self): if not gstreamer_is_working: self.stop() from blaplay.blagui import blaguiutils blaguiutils.error_dialog( "Error", "Failed to construct GStreamer pipeline. Make sure " "GStreamer 0.10, its Python bindings, and gst-plugins-base " "and gst-plugins-good are installed.") return False audio_sink = gst.Bin() filt = gst.element_factory_make("capsfilter") filt.set_property( "caps", gst.caps_from_string("audio/x-raw-float," "rate=(int)44100," "channels=(int)2," "width=(int)32," "depth=(int)32," "endianness=(int)1234")) self.__equalizer = gst.element_factory_make("equalizer-10bands") tee = gst.element_factory_make("tee") queue = gst.element_factory_make("queue") queue.set_property("silent", True) def new_buffer(sink): self.emit("new_buffer", sink.emit("pull_buffer")) appsink = gst.element_factory_make("appsink") appsink.set_property("drop", True) appsink.set_property("sync", True) appsink.set_property("emit_signals", True) appsink.connect("new_buffer", new_buffer) sink = gst.element_factory_make("autoaudiosink") self.__volume = gst.element_factory_make("volume") elements = [filt, self.__equalizer, tee, queue, appsink, self.__volume, sink] map(audio_sink.add, elements) pad = elements[0].get_static_pad("sink") audio_sink.add_pad(gst.GhostPad("sink", pad)) gst.element_link_many(filt, self.__equalizer, tee) gst.element_link_many(tee, self.__volume, sink) gst.element_link_many(tee, queue, appsink) video_sink = gst.element_factory_make("xvimagesink") video_sink.set_property("force_aspect_ratio", True) self.__bin = gst.element_factory_make("playbin2") self.__bin.set_property("audio_sink", audio_sink) self.__bin.set_property("buffer_duration", 500 * gst.MSECOND) self.__bin.set_property("video_sink", video_sink) self.__bin.connect("about_to_finish", self.__about_to_finish) self.__bin.set_state(gst.STATE_READY) bus = self.__bin.get_bus() bus.add_signal_watch() bus.enable_sync_message_emission() self.__message_id = bus.connect("message", self.__message) self.__sync_message_id = bus.connect( "sync-message::element", self.__sync_message) if blacfg.getboolean("player", "muted"): volume = 0 else: volume = blacfg.getfloat("player", "volume") * 100 self.set_volume(volume) self.enable_equalizer(blacfg.getboolean("player", "use.equalizer")) return True