def _addStreamFromPad(self, pad): self._maybeQueryDuration(pad) self.debug("adding stream from pad %s caps %s", pad, pad.props.caps) stream = get_stream_for_pad(pad) self.current_streams.append(stream) return stream
def _newVideoPadCb(self, pad): """ a new video pad was found """ self.debug("pad %r", pad) self._addPadProbes(pad) thumbnail = self._getThumbnailFilenameFromPad(pad) self.thumbnails[pad] = thumbnail have_thumbnail = os.path.exists(thumbnail) if have_thumbnail: self.debug("we already have a thumbnail %s for %s", thumbnail, pad) sink = gst.element_factory_make("fakesink") # use this and not fakesink.props.num_buffers = 1 to avoid some # not-expected errors when discovering pictures eossir = EOSSir() self.dynamic_elements.extend([eossir, sink]) self.pipeline.add(eossir, sink) eossir.set_state(gst.STATE_PLAYING) sink.set_state(gst.STATE_PLAYING) pad.link(eossir.get_pad("sink")) eossir.link(sink) return stream = get_stream_for_pad(pad) if isinstance(stream, VideoStream) and not stream.is_image: self._addVideoBufferProbe(pad) queue = gst.element_factory_make("queue") queue.props.max_size_bytes = 5 * 1024 * 1024 queue.props.max_size_time = 5 * gst.SECOND vscale = gst.element_factory_make("videoscale") vscale.props.method = 0 csp = gst.element_factory_make("ffmpegcolorspace") pngenc = gst.element_factory_make("pngenc") pngenc.props.snapshot = True pngsink = gst.element_factory_make("filesink") pngsink.props.location = thumbnail self.dynamic_elements.extend([queue, vscale, csp, pngenc, pngsink]) self.pipeline.add(queue, vscale, csp, pngenc, pngsink) gst.element_link_many(queue, csp, vscale) vscale.link( pngenc, gst.Caps( "video/x-raw-rgb,width=[1,96],height=[1,96];video/x-raw-yuv,width=[1,96],height=[1,96]" )) gst.element_link_many(pngenc, pngsink) pad.link(queue.get_pad("sink")) for element in [queue, vscale, csp, pngenc, pngsink]: element.sync_state_with_parent()
def addStreams(self, element, factory): """ Adds the good streams to the corresponding factory """ pads = element.get_static_pad_templates() if not factory: return False for padTmp in pads: pad = gst.Pad(padTmp.get()) if pad.get_caps() == "ANY": #FIXME return False if padTmp.direction == gst.PAD_SRC: stream = get_stream_for_pad(pad) factory.addInputStream(stream) elif padTmp.direction == gst.PAD_SINK: stream = get_stream_for_pad(pad) factory.addOutputStream(stream) return True
def addStreams(self, element, factory): """ Adds the good streams to the corresponding factory """ pads = element.get_static_pad_templates() if not factory: return False for padTmp in pads: pad = gst.Pad (padTmp.get()) if pad.get_caps() == "ANY": #FIXME return False if padTmp.direction == gst.PAD_SRC: stream = get_stream_for_pad(pad) factory.addInputStream(stream) elif padTmp.direction == gst.PAD_SINK: stream = get_stream_for_pad(pad) factory.addOutputStream(stream) return True
def _newVideoPadCb(self, pad): """ a new video pad was found """ self.debug("pad %r", pad) self._addPadProbes(pad) thumbnail = self._getThumbnailFilenameFromPad(pad) self.thumbnails[pad] = thumbnail have_thumbnail = os.path.exists(thumbnail) if have_thumbnail: self.debug("we already have a thumbnail %s for %s", thumbnail, pad) sink = gst.element_factory_make("fakesink") # use this and not fakesink.props.num_buffers = 1 to avoid some # not-expected errors when discovering pictures eossir = EOSSir() self.dynamic_elements.extend([eossir, sink]) self.pipeline.add(eossir, sink) eossir.set_state(gst.STATE_PLAYING) sink.set_state(gst.STATE_PLAYING) pad.link(eossir.get_pad("sink")) eossir.link(sink) return stream = get_stream_for_pad(pad) if isinstance(stream, VideoStream) and not stream.is_image: self._addVideoBufferProbe(pad) queue = gst.element_factory_make("queue") queue.props.max_size_bytes = 5 * 1024 * 1024 queue.props.max_size_time = 5 * gst.SECOND vscale = gst.element_factory_make("videoscale") vscale.props.method = 0 csp = gst.element_factory_make("ffmpegcolorspace") pngenc = gst.element_factory_make("pngenc") pngenc.props.snapshot = True pngsink = gst.element_factory_make("filesink") pngsink.props.location = thumbnail self.dynamic_elements.extend([queue, vscale, csp, pngenc, pngsink]) self.pipeline.add(queue, vscale, csp, pngenc, pngsink) gst.element_link_many(queue, csp, vscale) vscale.link( pngenc, gst.Caps("video/x-raw-rgb,width=[1,96],height=[1,96];video/x-raw-yuv,width=[1,96],height=[1,96]") ) gst.element_link_many(pngenc, pngsink) pad.link(queue.get_pad("sink")) for element in [queue, vscale, csp, pngenc, pngsink]: element.sync_state_with_parent()
def _newPadCb(self, pad): stream = get_stream_for_pad(pad) if isinstance(stream, TextStream): self.info("skipping subtitle pad") return self._addPadProbes(pad) queue = gst.element_factory_make('queue') fakesink = gst.element_factory_make('fakesink') fakesink.props.num_buffers = 1 self.dynamic_elements.append(queue) self.dynamic_elements.append(fakesink) self.pipeline.add(queue, fakesink) pad.link(queue.get_pad('sink')) queue.link(fakesink) queue.sync_state_with_parent() fakesink.sync_state_with_parent()
def getTeeForFactoryStream(self, factory, stream=None, automake=False): """ Fetches the C{Tee} currently used in the C{gst.Pipeline} for the given L{SourceFactory}. @param factory: The factory to search. @type factory: L{SourceFactory} @param stream: The stream of the factory to use. If not specified, then a random stream from that factory will be used. @type stream: L{MultimediaStream} @param automake: If set to True, then if there is not a C{Tee} already created for the given factory/stream, one will be created, added to the list of controlled tees and added to the C{gst.Pipeline}. @raise PipelineError: If the factory isn't used in this pipeline. @raise PipelineError: If the factory isn't a L{SourceFactory}. @raise PipelineError: If a C{Tee} needed to be created but the creation of that C{Tee} failed. @return: The C{Tee} corresponding to the given factory/stream or None if there are none for the given factory. @rtype: C{gst.Element} """ self.debug("factory:%r , stream:%r, automake:%r", factory, stream, automake) if not isinstance(factory, SourceFactory): raise PipelineError("Given ObjectFactory isn't a SourceFactory") stream_entry = self._getStreamEntryForFactoryStream(factory, stream) bin_stream_entry = stream_entry.findBinEntry() if bin_stream_entry is None: raise PipelineError("couldn't find bin entry") bin = bin_stream_entry.bin if stream_entry.tee is not None: stream_entry.tee_use_count += 1 # have an existing tee, return it return stream_entry.tee if not automake: raise PipelineError("no automake") self.debug("Really creating a tee") # get the source pads pads = get_src_pads_for_stream(bin, None) # get the corresponding streams streams = [get_stream_for_pad(pad, store_pad=True) for pad in pads] # find the pad that matches the given stream best if stream is None: if len(streams) == 1: stream = streams[0] else: raise PipelineError("bin has multiple compatible pads") stream, rank = match_stream(stream, streams) if stream is None: raise PipelineError("bin has no compatible source pads") srcpad = stream.pad self.debug("Using pad %r", srcpad) stream_entry.tee = gst.element_factory_make("tee") self._pipeline.add(stream_entry.tee) stream_entry.tee_use_count += 1 stream_entry.tee.set_state(STATE_PAUSED) self.debug("Linking pad %r to tee", pads[0]) srcpad.link_full(stream_entry.tee.get_pad("sink"), gst.PAD_LINK_CHECK_NOTHING) return stream_entry.tee
def getTeeForFactoryStream(self, factory, stream=None, automake=False): """ Fetches the C{Tee} currently used in the C{gst.Pipeline} for the given L{SourceFactory}. @param factory: The factory to search. @type factory: L{SourceFactory} @param stream: The stream of the factory to use. If not specified, then a random stream from that factory will be used. @type stream: L{MultimediaStream} @param automake: If set to True, then if there is not a C{Tee} already created for the given factory/stream, one will be created, added to the list of controlled tees and added to the C{gst.Pipeline}. @raise PipelineError: If the factory isn't used in this pipeline. @raise PipelineError: If the factory isn't a L{SourceFactory}. @raise PipelineError: If a C{Tee} needed to be created but the creation of that C{Tee} failed. @return: The C{Tee} corresponding to the given factory/stream or None if there are none for the given factory. @rtype: C{gst.Element} """ self.debug("factory:%r , stream:%r, automake:%r", factory, stream, automake) if not isinstance(factory, SourceFactory): raise PipelineError("Given ObjectFactory isn't a SourceFactory") stream_entry = self._getStreamEntryForFactoryStream(factory, stream) bin_stream_entry = stream_entry.findBinEntry() if bin_stream_entry is None: raise PipelineError("couldn't find bin entry") bin = bin_stream_entry.bin if stream_entry.tee is not None: stream_entry.tee_use_count += 1 # have an existing tee, return it return stream_entry.tee if not automake: raise PipelineError("no automake") self.debug("Really creating a tee") # get the source pads pads = get_src_pads_for_stream(bin, None) # get the corresponding streams streams = [get_stream_for_pad(pad, store_pad=True) for pad in pads] # find the pad that matches the given stream best if stream is None: if len(streams) == 1: stream = streams[0] else: raise PipelineError("bin has multiple compatible pads") stream, rank = match_stream(stream, streams) if stream is None: raise PipelineError("bin has no compatible source pads") srcpad = stream.pad self.debug("Using pad %r", srcpad) stream_entry.tee = gst.element_factory_make("tee") self._pipeline.add(stream_entry.tee) stream_entry.tee_use_count += 1 stream_entry.tee.set_state(STATE_PAUSED) self.debug("Linking pad %r to tee", pads[0]) srcpad.link(stream_entry.tee.get_pad("sink")) return stream_entry.tee
def _addStreamFromPad(self, pad): stream = get_stream_for_pad(pad) self.current_streams.append(stream) return stream