diff --git a/modules/core/engine.py b/modules/core/engine.py index a35f17141a0a1b8c395b965dda8c2b9f38f983e1..04d166badf611a92b3d7255e7d5f7eb8f904552f 100644 --- a/modules/core/engine.py +++ b/modules/core/engine.py @@ -405,7 +405,7 @@ class Player: return if transition == TransitionType.FADE: - self.mixer.fade_out(entry.channel, entry.volume) + self.mixer.fade_out(entry.channel) else: self.mixer.channel_volume(entry.channel, 0) @@ -435,7 +435,7 @@ class Player: self.logger.info(f"Fading out channel '{dirty_channel}'") self.connector.enable_transaction() - self.mixer_fallback.fade_out(dirty_channel, 100) + self.mixer_fallback.fade_out(dirty_channel) self.connector.disable_transaction() def clean_up(): diff --git a/modules/core/mixer.py b/modules/core/mixer.py index 5db6e28c8ba47a9ade79a24cb75ff69efe9ada6c..8a92b7f79f583e6aeaabb9747c2bd2f7ea27034c 100644 --- a/modules/core/mixer.py +++ b/modules/core/mixer.py @@ -37,6 +37,26 @@ class MixerType(Enum): + +class MixerUtil: + """ + Little helpers for the mixer. + """ + + @staticmethod + def channel_status_dict(status): + """ + Transforms a channel status string to a dictionary. + """ + s = {} + pairs = status.split(" ") + for pair in pairs: + kv = pair.split("=") + s[kv[0]] = kv[1] + return s + + + class Mixer(): """ A virtual mixer. @@ -154,18 +174,41 @@ class Mixer(): return self.mixer_channels() + # + # Channel + # + + def channel_number(self, channel): + """ + Returns the channel number for the given channel ID. + + Args: + channel (Channel): The channel + + Returns: + (Integer): The channel number + """ + channels = self.mixer_channels() + index = channels.index(channel) + if index < 0: + self.logger.critical(f"There's no valid channel number for channel ID '{channel.value}'") + return None + return index + + def channel_status(self, channel_number): """ Retrieves the status of a channel identified by the channel number. + + Args: + channel_number (Integer): The channel number + + Returns: + (String): Channel status info as a String """ return self.connector.send_lqc_command(self.mixer_id.value, "mixer_status", channel_number) - # - # Channel - # - - def channel_select(self, channel, select): """ Selects/deselects some mixer channel @@ -217,6 +260,20 @@ class Mixer(): self.logger.critical("Ran into exception when activating channel. Reason: " + str(e)) + def channel_current_volume(self, channel): + """ + Retrieves the current volume of the channel. + """ + channel_number = self.channel_number(channel.value) + status = self.channel_status(channel_number) + channel_status = MixerUtil.channel_status_dict(status) + volume = channel_status.get("volume") + if volume: + return int(volume.split("%")[0]) + else: + self.logger.error(f"Invalid volume for channel {channel.value} (status: '{status}'") + return 0 + def channel_volume(self, channel, volume): """ @@ -278,6 +335,15 @@ class Mixer(): (Boolean): `True` if successful """ try: + current_volume = self.channel_current_volume(channel) + + if current_volume == volume: + self.logger.warning(f"Current volume for channel {channel.value} is already at target volume of {volume}% SKIPPING...") + return + elif current_volume > volume: + self.logger.warning(f"Current volume {current_volume}% of channel {channel.value} exceeds target volume of {volume}% SKIPPING...") + return + fade_in_time = float(self.config.get("fade_in_time")) if fade_in_time > 0: @@ -313,9 +379,9 @@ class Mixer(): - def fade_out(self, channel, volume): + def fade_out(self, channel, volume=None): """ - Performs a fade-out for the given channel. + Performs a fade-out for the given channel starting at it's current volume. Args: channel (Channel): The channel to fade @@ -325,10 +391,18 @@ class Mixer(): (Boolean): `True` if successful """ try: + current_volume = self.channel_current_volume(channel) + if not volume: + volume = current_volume + + if current_volume == 0: + self.logger.warning(f"Current volume for channel {channel.value} is already at target volume of 0%. SKIPPING...") + return + fade_out_time = float(self.config.get("fade_out_time")) if fade_out_time > 0: - step = abs(fade_out_time) / volume + step = abs(fade_out_time) / current_volume msg = "Starting to fading-out '%s'. Step is %ss." % (channel, str(step)) self.logger.info(SU.pink(msg)) @@ -353,4 +427,4 @@ class Mixer(): except LQConnectionError as e: self.logger.critical(str(e)) return False - return True \ No newline at end of file + return True