using System; using System.Collections.Generic; using System.Globalization; using System.IO; using System.Runtime.InteropServices; using WMPLib; namespace MusicMetaTagger.UI { /// /// /// /// Attribute Reference http://msdn2.microsoft.com/en-us/library/bb248367.aspx /// public class MediaPlayerLibraryInterface : IMusicLibraryInterface { #region Private members /// /// Relates TrackQuery object to the /// private Dictionary _trackQueryTracks; /// /// Media player interface object (COM) /// private WindowsMediaPlayer _windowsMediaPlayer; #endregion #region Private methods /// /// Gets the IWMPMedia track from the associated TrackQueryStatus. /// /// The track query status. /// private IWMPMedia GetTrack(TrackQueryStatus trackQueryStatus) { if (!_trackQueryTracks.ContainsKey(trackQueryStatus)) throw new ApplicationException("Doesn't contain track" + trackQueryStatus.TrackTitle); return _trackQueryTracks[trackQueryStatus]; } #endregion #region IMusicLibraryInterface methods /// /// Gets the track queries. /// /// The library query. /// The callback. /// public List GetTrackQueries(LibraryQuery libraryQuery, IProgressCallback callback) { if (_trackQueryTracks == null) _trackQueryTracks = new Dictionary(); var trackQueries = new List(); callback.SetText("Opening Media Player Library"); _windowsMediaPlayer = new WindowsMediaPlayer(); var mediaCollection = _windowsMediaPlayer.mediaCollection; callback.SetText("Getting tracks"); var playlist = mediaCollection.getAll(); var trackCount = libraryQuery.ScanLimit <= 0 ? playlist.count : Math.Min(playlist.count, libraryQuery.ScanLimit); callback.SetRange(0, trackCount); callback.Begin(); for (var i = 1; i <= trackCount; i++) { callback.Increment(1); if (i%5 == 0 || i == trackCount) callback.SetText(string.Format("Scanning track# {0} / {1}, Found {2} matches", i, trackCount, trackQueries.Count)); if (callback.IsAborting) break; var track = playlist.Item[i]; var trackQuery = new TrackQueryStatus { TrackTitle = track.getItemInfo("Title"), ArtistName = track.getItemInfo("Author"), AlbumTitle = track.getItemInfo("AlbumId") }; var durationString = track.getItemInfo("Duration"); if (string.IsNullOrEmpty(durationString)) durationString = "1"; trackQuery.TrackLength = new TimeSpan(0, 0, 0, Convert.ToInt32(Convert.ToDouble(durationString))); var originalIndexString = track.getItemInfo("OriginalIndex"); if (!string.IsNullOrEmpty(originalIndexString)) trackQuery.TrackNumber = Convert.ToInt32(originalIndexString); var acquisitionTime = Convert.ToDateTime(track.getItemInfo("AcquisitionTime")); if (libraryQuery.AddedAfter > acquisitionTime) continue; if (libraryQuery.BlankGenre && !string.IsNullOrEmpty(track.getItemInfo("Genre"))) continue; if (libraryQuery.BlankRating && !string.IsNullOrEmpty(track.getItemInfo("UserRating"))) continue; if (libraryQuery.BlankYear && !string.IsNullOrEmpty(track.getItemInfo("ReleaseDateYear"))) continue; if (!libraryQuery.MatchTrackQuery(trackQuery)) continue; trackQueries.Add(trackQuery); _trackQueryTracks.Add(trackQuery, track); } return trackQueries; } /// /// Updates the album art. /// /// /// http://msdn2.microsoft.com/en-us/library/aa392196.aspx /// /// The track query. /// The album art file info. /// if set to true [overwrite]. /// True if update was successful, false otherwise public bool UpdateAlbumArt(TrackQueryStatus trackQuery, FileInfo albumArt, bool overwrite) { //IWMPMedia track = GetTrack(trackQuery); //IWMPMedia3 t = track as IWMPMedia3; //Object o = t.getItemInfoByType("WM/Picture", "", 0); //int [] ha; //WMPicture pic = new WMPicture(); //Marshal.Copy(ha., 0, pic, ); // http://www.ureader.com/message/33380790.aspx return false; } /// /// Updates the genre. /// /// The track query. /// The genre. /// if set to true [overwrite]. /// True if update was successful, false otherwise public bool UpdateGenre(TrackQueryStatus trackQuery, string genre, bool overwrite) { var track = GetTrack(trackQuery); if (string.IsNullOrEmpty(track.getItemInfo("WM/Genre")) || overwrite) { track.setItemInfo("WM/Genre", genre); return true; } return false; } /// /// Updates the year. /// /// The track query. /// The year. /// if set to true [overwrite]. /// True if update was successful, false otherwise public bool UpdateYear(TrackQueryStatus trackQuery, int year, bool overwrite) { var track = GetTrack(trackQuery); if (track.isReadOnlyItem("WM/Year")) return false; if (string.IsNullOrEmpty(track.getItemInfo("WM/Year")) || overwrite) { track.setItemInfo("WM/Year", year.ToString(CultureInfo.InvariantCulture)); return true; } return false; } /// /// Updates the rating. /// /// The track query. /// The rating from 0 to 100. /// if set to true overwrite existing value. /// True if update was successful, false otherwise public bool UpdateRating(TrackQueryStatus trackQuery, int rating, bool overwrite) { var track = GetTrack(trackQuery); if (Convert.ToInt32(track.getItemInfo("UserRating")) == 0 || overwrite) { track.setItemInfo("UserRating", rating.ToString(CultureInfo.InvariantCulture)); return true; } return false; } public bool AddComment(TrackQueryStatus trackQuery, string comment) { // TODO: implement return false; } /// /// Returns true if the trackQuery represents an Mp3. /// /// public bool IsMp3(TrackQueryStatus trackQuery) { var track = GetTrack(trackQuery); try { var trackFileInfo = new FileInfo(track.sourceURL); return trackFileInfo.Extension.ToUpper() == "MP3"; } catch { } return false; } /// /// Returns the Mp3 represented by this trackQuery /// /// /// public FileInfo GetMp3FileInfo(TrackQueryStatus trackQuery) { var track = GetTrack(trackQuery); try { return new FileInfo(track.sourceURL); } catch { } return null; } [StructLayout(LayoutKind.Sequential, Pack = 1)] private struct WMPicture { public readonly IntPtr pwszMIMEType; public readonly byte bPictureType; public readonly IntPtr pwszDescription; [MarshalAs(UnmanagedType.U4)] public readonly int dwDataLen; public readonly IntPtr pbData; } #endregion } }