/// <summary>
        /// Fade out channels in the audio config. Can also stop the playback after the fade out.
        /// </summary>
        /// <param name="audioConfig">The target audio config</param>
        /// <param name="duration">Duration of the fade in phase</param>
        /// <param name="autoStop">Auto stop the audio after the playback</param>
        /// <param name="parent">The target parent transform</param>
        /// <param name="onComplete">Callback after the fade out completed</param>
        public static void FadeOut(this AudioConfig audioConfig, float duration = 1.0f, bool autoStop = true, Transform parent = null, Action onComplete = null)
        {
            var channels = audioConfig.GetChannels(parent);

            foreach (var channel in channels)
            {
                FadeOut(channel, duration, autoStop, onComplete);
            }
        }
        /// <summary>
        /// Fade channels in the audio config from current volume to a volume.
        /// </summary>
        /// <param name="audioConfig">The target audio config</param>
        /// <param name="volume">To volume</param>
        /// <param name="duration">Duration of the fade phase</param>
        /// <param name="parent">The target parent transform</param>
        /// <param name="onComplete">Callback after the fade completed</param>
        public static void FadeTo(this AudioConfig audioConfig, float volume, float duration = 1.0f, Transform parent = null, Action onComplete = null)
        {
            var channels = audioConfig.GetChannels(parent);

            foreach (var channel in channels)
            {
                AudioSystem.Instance.FadeTo(channel, volume, duration, onComplete);
            }
        }
        /// <summary>
        /// Stop the audio
        /// </summary>
        /// <param name="audioConfig">The target audio config</param>
        /// <param name="parent">The target parent transform</param>
        /// <param name="removeOnCompleteCallback">Remove the callback</param>
        /// <returns>False if the channel is invalid (not from this Audio System) or already stopped</returns>
        public static void Stop(this AudioConfig audioConfig, Transform parent = null, bool removeOnCompleteCallback = false)
        {
            var channels = audioConfig.GetChannels(parent);

            // Use for loop here because the collection will be modified during the iteration
            for (var i = channels.Count - 1; i >= 0; --i)
            {
                var channel = channels[i];
                AudioSystem.Instance.Stop(channel, true);
                audioConfig.RemoveOccupiedChannel(channel);

                var callback = audioConfig.Callbacks.GetAndRemove(channel);
                if (callback != null && !removeOnCompleteCallback)
                {
                    callback.Invoke();
                }
            }
        }