using NAudio.Wave;

namespace qtcnet_client.Services
{
    public class AudioService : IDisposable
    {
        public WaveOutEvent? OutputDevice { get; set; }
        public AudioFileReader? AudioFileReader { get; set; }

        public event EventHandler<SoundEndedEventArgs>? OnSoundEnded;
        public void PlaySoundEffect(string soundName)
        {
            if (!File.Exists($"./Sounds/{soundName}.wav")) return;

            OutputDevice = new WaveOutEvent();
            AudioFileReader = new AudioFileReader($"./Sounds/{soundName}.wav");
            OutputDevice.Init(AudioFileReader);
            OutputDevice.Play();

            return;
        }

        public void PlaySoundEffectWithEventString(string soundName, string eventString)
        {
            if (!File.Exists($"./Sounds/{soundName}.wav")) return;

            OutputDevice = new WaveOutEvent();
            AudioFileReader = new AudioFileReader($"./Sounds/{soundName}.wav");
            OutputDevice.Init(AudioFileReader);
            OutputDevice.Play();

            OutputDevice.PlaybackStopped += (sender, args) => OnSoundEnded?.Invoke(null, new SoundEndedEventArgs { EventString = eventString });
        }

        public void PlaySoundLooped(string soundName, int loopCount)
        {
            if (!File.Exists($"./Sounds/{soundName}.wav")) return;

            OutputDevice = new WaveOutEvent();
            AudioFileReader = new AudioFileReader($"./Sounds/{soundName}.wav");
            OutputDevice.Init(AudioFileReader);
            OutputDevice.Play();

            int i = 0;
            OutputDevice.PlaybackStopped += (sender, args) =>
            {
                i++;
                if (i == loopCount) { OutputDevice.PlaybackStopped += null; return; }

                AudioFileReader.Seek(0, SeekOrigin.Begin);
                OutputDevice.Play();
            };
        }

        public void Dispose()
        {
            GC.SuppressFinalize(this);

            OutputDevice?.Dispose();
            OutputDevice = null;
            AudioFileReader?.Dispose();
            AudioFileReader = null;
        }

    }

    public class SoundEndedEventArgs : EventArgs
    {
        public string EventString { get; set; } = "UNKNOWN";
    }
}
