using System; using System.Collections.Generic; using ANX.Framework.NonXNA.Development; // This file is part of the ANX.Framework created by the // "ANX.Framework developer group" and released under the Ms-PL license. // For details see: http://anxframework.codeplex.com/license namespace ANX.Framework.Media { [PercentageComplete(100)] [Developer("AstrorEnales")] [TestState(TestStateAttribute.TestState.Untested)] public sealed class MediaQueue { private readonly List queue; private readonly List shuffledQueue; private int activeSongIndex; #region Public public int Count { get { return queue.Count; } } public int ActiveSongIndex { get { return activeSongIndex; } set { if (Count <= 0) return; ActiveSong.Stop(); activeSongIndex = Math.Min(value, queue.Count); ActiveSong.Play(); } } public Song ActiveSong { get { return shuffledQueue.Count <= 0 ? null : shuffledQueue[ActiveSongIndex]; } } public Song this[int index] { get { return shuffledQueue[index]; } } #endregion #region Constructor internal MediaQueue() { queue = new List(); shuffledQueue = new List(); } ~MediaQueue() { queue.Clear(); shuffledQueue.Clear(); } #endregion #region Play internal void Play(Song song) { if (song == null) throw new ArgumentNullException("song"); Clear(); queue.Add(song); shuffledQueue.Add(song); ActiveSong.Play(); } internal void Play(SongCollection songCollection) { if (songCollection == null) throw new ArgumentNullException("songCollection"); Clear(); queue.AddRange(songCollection); UpdateOrder(); ActiveSong.Play(); } internal void Play(SongCollection songCollection, int index) { if (songCollection == null) throw new ArgumentNullException("songCollection"); Clear(); ActiveSongIndex = index; queue.AddRange(songCollection); UpdateOrder(); ActiveSong.Play(); } #endregion internal void UpdateOrder() { if (Count <= 0) return; Song currentPlayingSong = ActiveSong; if (MediaPlayer.IsShuffled) Shuffle(); else { shuffledQueue.Clear(); shuffledQueue.AddRange(queue.ToArray()); } activeSongIndex = shuffledQueue.IndexOf(currentPlayingSong); } private void Clear() { Stop(); ActiveSongIndex = 0; queue.Clear(); shuffledQueue.Clear(); } internal void Stop() { if(ActiveSong != null) ActiveSong.Stop(); } private void Shuffle() { var rand = new Random(); int n = queue.Count; while (n > 1) { int k = rand.Next(n); n--; Song value = shuffledQueue[k]; shuffledQueue[k] = shuffledQueue[n]; shuffledQueue[n] = value; } } #region MoveNext internal bool MoveNext(bool isRepeating) { if (Count <= 0) return false; ActiveSong.Stop(); if (ActiveSongIndex < Count - 1) ActiveSongIndex++; else { ActiveSongIndex = 0; if (isRepeating == false) return false; } ActiveSong.Play(); return true; } #endregion #region MovePrevious internal void MovePrevious() { if (Count <= 0) return; ActiveSong.Stop(); if (ActiveSongIndex > 0) ActiveSongIndex--; else ActiveSongIndex = Count - 1; ActiveSong.Play(); } #endregion } }