/// <summary> /// Removes and audio stream from a mixer. /// </summary> /// <param name="audioStream">The audio stream.</param> /// <param name="mixerChannel">The mixer channel.</param> public static void RemoveFromMixer(AudioStream audioStream, int mixerChannel) { if (audioStream == null || !audioStream.IsAudioLoaded()) throw new Exception("Audio file null or not audio not loaded"); if (mixerChannel == int.MinValue) throw new Exception("Mixer channel not initialized"); //lock (Lock) { DebugHelper.WriteLine($"RemoveFromMixer {audioStream.Description} {audioStream.Channel}..."); BassMix.BASS_Mixer_ChannelPause(audioStream.Channel); Bass.BASS_ChannelLock(mixerChannel, true); foreach (var channel in audioStream.Channels) { BassMix.BASS_Mixer_ChannelRemove(channel); } Bass.BASS_ChannelLock(mixerChannel, false); DebugHelper.WriteLine("done"); } }
public static void LoadAudio(AudioStream audioStream) { // abort if audio data already loaded if (audioStream.IsAudioLoaded()) return; AudioDataHelper.LoadAudioData(audioStream); var channel = Bass.BASS_StreamCreateFile(audioStream.AudioData.DataPointer, 0, audioStream.AudioData.Data.Length, BASSFlag.BASS_SAMPLE_FLOAT | BASSFlag.BASS_STREAM_DECODE | BASSFlag.BASS_STREAM_PRESCAN); audioStream.AddChannel(channel); if (audioStream.Channel == 0) throw new Exception("Cannot load " + audioStream.Filename + ". Error code: " + Bass.BASS_ErrorGetCode()); DebugHelper.WriteLine("Creating reverse FX stream " + audioStream.Description + "..."); audioStream.AddChannel(BassFx.BASS_FX_ReverseCreate(audioStream.Channel, 1, BASSFlag.BASS_STREAM_DECODE)); if (audioStream.Channel == 0) throw new Exception("Cannot load " + audioStream.Filename + ". Error code: " + Bass.BASS_ErrorGetCode()); Bass.BASS_ChannelSetAttribute(audioStream.Channel, BASSAttribute.BASS_ATTRIB_REVERSE_DIR, (float)BASSFXReverse.BASS_FX_RVS_FORWARD); DebugHelper.WriteLine("Creating tempo FX stream " + audioStream.Description + "..."); audioStream.AddChannel(BassFx.BASS_FX_TempoCreate(audioStream.Channel, BASSFlag.BASS_FX_FREESOURCE | BASSFlag.BASS_STREAM_DECODE)); if (audioStream.Channel == 0) throw new Exception("Cannot load " + audioStream.Filename + ". Error code: " + Bass.BASS_ErrorGetCode()); DebugHelper.WriteLine("Calculating track length " + audioStream.Description + "..."); audioStream.Length = Bass.BASS_ChannelGetLength(audioStream.Channel); audioStream.DefaultSampleRate = GetSampleRate(audioStream.Channel); SetReplayGain(audioStream); SetPosition(audioStream, 0); }
/// <summary> /// Sets the length of an audio stream. /// </summary> /// <param name="audioStream">The audio stream.</param> public static void SetLength(AudioStream audioStream) { if (audioStream == null || !audioStream.IsAudioLoaded()) throw new Exception("Audio file null or not audio not loaded"); audioStream.Length = Bass.BASS_ChannelGetLength(audioStream.Channel); }
/// <summary> /// Adds an audio stream to a mixer /// </summary> /// <param name="audioStream">The audio stream.</param> /// <param name="mixerChannel">The mixer channel.</param> public static void AddToMixer(AudioStream audioStream, int mixerChannel) { if (audioStream == null || !audioStream.IsAudioLoaded()) throw new Exception("Audio file null or not audio not loaded"); if (mixerChannel == int.MinValue) throw new Exception("Mixer channel not initialized"); DebugHelper.WriteLine($"AddToMixer {audioStream.Description} {mixerChannel} {audioStream.Channel}..."); AddChannelToMixer(audioStream.Channel, mixerChannel); DebugHelper.WriteLine("done"); }
/// <summary> /// Does an audio stream power down effect asynchronously /// </summary> /// <param name="audioStream">The audio stream.</param> private static void PowerDownAsync(AudioStream audioStream) { if (audioStream == null || !audioStream.IsAudioLoaded()) return; var freq = audioStream.DefaultSampleRate; var interval = (int)(BpmHelper.GetDefaultLoopLength(audioStream.Bpm) * 1000) / 128; // set the volume slide Bass.BASS_ChannelSlideAttribute(audioStream.Channel, BASSAttribute.BASS_ATTRIB_VOL, 0F, interval * 8); var percentValue = 0.70; while (freq > 100) { percentValue = percentValue / 1.2; interval = (int)(interval * 0.9D); freq = (int)(audioStream.DefaultSampleRate * percentValue); if (freq <= 100 || audioStream.Channel == int.MinValue) continue; Bass.BASS_ChannelSlideAttribute(audioStream.Channel, BASSAttribute.BASS_ATTRIB_FREQ, freq, interval); Thread.Sleep(interval); } Pause(audioStream); if (!audioStream.IsAudioLoaded()) return; Bass.BASS_ChannelSetAttribute(audioStream.Channel, BASSAttribute.BASS_ATTRIB_FREQ, audioStream.DefaultSampleRate); SetVolume(audioStream, 100M); }
/// <summary> /// Sets the replay gain for a channel. /// </summary> /// <param name="audioStream">The audio stream.</param> private static void SetReplayGain(AudioStream audioStream) { if (audioStream == null || !audioStream.IsAudioLoaded()) throw new Exception("Audio file null or not audio not loaded"); if (!audioStream.IsGainChannelInitialized() && audioStream.Gain == 0) return; var volume = DecibelToPercent(audioStream.Gain); DebugHelper.WriteLine("SetReplayGain for " + audioStream + " to " + volume); if (!audioStream.IsGainChannelInitialized()) { audioStream.GainChannel = Bass.BASS_ChannelSetFX(audioStream.Channel, BASSFXType.BASS_FX_BFX_VOLUME, int.MaxValue); } var volumeParameters = new BASS_BFX_VOLUME(volume, BASSFXChan.BASS_BFX_CHANALL); Bass.BASS_FXSetParameters(audioStream.GainChannel, volumeParameters); }
/// <summary> /// Does an audio stream power down effect asynchronously /// </summary> /// <param name="audioStream">The audio stream.</param> private static void SmoothPauseAsync(AudioStream audioStream) { if (audioStream == null || !audioStream.IsAudioLoaded()) return; var volume = ((float)GetVolume(audioStream)) / 100F; SetVolumeSlide(audioStream, volume, 0F, 0.15D); Thread.Sleep(150); if (!audioStream.IsAudioLoaded()) return; BassMix.BASS_Mixer_ChannelPause(audioStream.Channel); SetVolume(audioStream, volume); }
/// <summary> /// Sets the duration and start/end volumes for an audio stream volume slide. /// </summary> /// <param name="audioStream">The audio stream.</param> /// <param name="startVolume">The start volume.</param> /// <param name="endVolume">The end volume.</param> /// <param name="sampleDuration">Sample length duration.</param> public static void SetVolumeSlide(AudioStream audioStream, float startVolume, float endVolume, long sampleDuration) { if (audioStream == null || !audioStream.IsAudioLoaded()) return; var seconds = audioStream.SamplesToSeconds(sampleDuration); SetVolumeSlide(audioStream, startVolume, endVolume, seconds); }
/// <summary> /// Gets the current audioStream position. /// </summary> /// <param name="audioStream">The audio stream.</param> /// <returns>The current audio stream position</returns> public static long GetPosition(AudioStream audioStream) { if (audioStream == null) return 0; return !audioStream.IsAudioLoaded() ? 0 : Bass.BASS_ChannelGetPosition(audioStream.Channel); }
/// <summary> /// Pause an audio stream /// </summary> /// <param name="audioStream">The audio stream.</param> public static void Pause(AudioStream audioStream) { if (audioStream == null || !audioStream.IsAudioLoaded()) return; BassMix.BASS_Mixer_ChannelPause(audioStream.Channel); }
/// <summary> /// Sets the audio stream position /// </summary> /// <param name="audioStream">The audio stream.</param> /// <param name="samplePosition">The audio stream position.</param> public static void SetPosition(AudioStream audioStream, long samplePosition) { if (audioStream == null || !audioStream.IsAudioLoaded()) return; if (samplePosition < 0 || samplePosition > audioStream.Length) return; var secondPosition = TimeFormatHelper.GetFormattedSeconds(audioStream.SamplesToSeconds(samplePosition)); DebugHelper.WriteLine($"SetPosition {audioStream.Description} {secondPosition} {samplePosition}"); Bass.BASS_ChannelSetPosition(audioStream.Channel, samplePosition); DebugHelper.WriteLine($"SetPosition END {audioStream.Description} {secondPosition} {samplePosition}"); }
/// <summary> /// Resets the audio stream pitch. /// </summary> /// <param name="audioStream">The audio stream.</param> public static void ResetPitch(AudioStream audioStream) { if (audioStream == null || !audioStream.IsAudioLoaded()) return; Bass.BASS_ChannelSetAttribute(audioStream.Channel, BASSAttribute.BASS_ATTRIB_TEMPO_PITCH, 0F); }
/// <summary> /// Sets the audio stream pitch, based on a percent pitch value (0 - 200, 100 being 'normal' pitch) /// </summary> /// <param name="audioStream">The audio stream.</param> /// <param name="pitch">The pitch.</param> public static void SetPitch(AudioStream audioStream, double pitch) { if (audioStream == null || !audioStream.IsAudioLoaded()) return; DebugHelper.WriteLine("SetPitch"); float sampleRate = audioStream.DefaultSampleRate; Bass.BASS_ChannelSetAttribute(audioStream.Channel, BASSAttribute.BASS_ATTRIB_TEMPO_FREQ, sampleRate); }
/// <summary> /// Unloads the audio of an audio stream /// </summary> /// <param name="audioStream">The audio stream.</param> public static void UnloadAudio(AudioStream audioStream) { if (audioStream == null || !audioStream.IsAudioLoaded()) throw new Exception("Audio file null or not audio not loaded"); DebugHelper.WriteLine($"UnloadAudio {audioStream.Description}..."); foreach (var channel in audioStream.Channels) { Bass.BASS_StreamFree(channel); } audioStream.Channels.Clear(); AudioDataHelper.UnloadAudioData(audioStream); DebugHelper.WriteLine("done"); }
/// <summary> /// Plays an audio stream /// </summary> /// <param name="audioStream">The audio stream.</param> public static void Play(AudioStream audioStream) { if (audioStream == null || !audioStream.IsAudioLoaded()) return; //lock (Lock) //{ DebugHelper.WriteLine("Play Audio Stream (" + audioStream.Description + ")"); BassMix.BASS_Mixer_ChannelPlay(audioStream.Channel); // } }
/// <summary> /// Gets the audio stream volume. /// </summary> /// <param name="audioStream">The audio stream.</param> /// <returns>The tracks volume</returns> public static decimal GetVolume(AudioStream audioStream) { if (audioStream == null || !audioStream.IsAudioLoaded()) return 0; return GetVolume(audioStream.Channel); }
/// <summary> /// Sets the duration and start/end volumes for an audio stream volume slide. /// </summary> /// <param name="audioStream">The audio stream.</param> /// <param name="startVolume">The start volume as a percentage (0 - 1).</param> /// <param name="endVolume">The end volume as a percentage (0 - 1).</param> /// <param name="seconds">The seconds.</param> public static void SetVolumeSlide(AudioStream audioStream, float startVolume, float endVolume, double seconds) { if (audioStream == null || !audioStream.IsAudioLoaded()) return; // set start volume SetVolume(audioStream, startVolume); var miliseconds = (int)(seconds * 1000); // set the volume slide Bass.BASS_ChannelSlideAttribute(audioStream.Channel, BASSAttribute.BASS_ATTRIB_VOL, endVolume, miliseconds); }