emmental/emmental/audio/replaygain.py

63 lines
2.4 KiB
Python

# Copyright 2022 (c) Anna Schumaker.
"""A custom Gst.Bin for selecting ReplayGain mode."""
import collections
from gi.repository import GObject
from gi.repository import Gst
RequestPads = collections.namedtuple("RequestPads", ["src", "sink"])
class Filter(Gst.Bin):
"""The ReplayGain filter element."""
mode = GObject.Property(type=str, default="disabled")
def __init__(self):
"""Initialize the ReplayGain element."""
super().__init__()
self._src = Gst.ElementFactory.make("output-selector")
self._sink = Gst.ElementFactory.make("input-selector")
self._rgalbum = Gst.ElementFactory.make("rgvolume")
self._rgtrack = Gst.ElementFactory.make("rgvolume")
self._rglimit = Gst.ElementFactory.make("rglimiter")
for elm in [self._src, self._rgalbum, self._rgtrack,
self._rglimit, self._sink]:
self.add(elm)
self._disabled = self.__request_pads(self._rglimit)
self._album_mode = self.__request_pads(self._rgalbum)
self._track_mode = self.__request_pads(self._rgtrack)
self._rgalbum.set_property("pre-amp", 6.0)
self._rgtrack.set_property("pre-amp", 6.0)
self._rgtrack.set_property("album-mode", False)
self._src.set_property("pad-negotiation-mode", 2)
self._src.set_property("active-pad", self._disabled.src)
self._sink.set_property("active-pad", self._disabled.sink)
self.__add_ghost_pad("sink", self._src)
self.__add_ghost_pad("src", self._sink)
self.connect("notify::mode", self.__notify_mode)
def __add_ghost_pad(self, pad: str, elm: Gst.Element) -> None:
self.add_pad(Gst.GhostPad.new(pad, elm.get_static_pad(pad)))
def __request_pads(self, elm: Gst.Element) -> RequestPads:
pads = RequestPads(src=self._src.request_pad_simple("src_%u"),
sink=self._sink.request_pad_simple("sink_%u"))
pads.src.link(elm.get_static_pad("sink"))
elm.get_static_pad("src").link(pads.sink)
return pads
def __notify_mode(self, filter: Gst.Bin, param) -> None:
match self.mode:
case "album": pads = self._album_mode
case "track": pads = self._track_mode
case _: pads = self._disabled
print(f"audio: setting ReplayGain mode to '{self.mode}'")
self._src.set_property("active-pad", pads.src)
self._sink.set_property("active-pad", pads.sink)