/// <summary> /// Instantiate a new playlist writer based on the specified key. /// </summary> /// <param name="key">The key identifying the writer.</param> /// <param name="root">The root path of the exported playlist.</param> /// <param name="name">The base name of this playlist file.</param> /// <param name="createSubdirectories"> /// A Boolean value indicating whether files in this playlist are located relative /// to the root (<b>true</b>) or are all located within the root itself (<b>false</b>). /// </param> /// <returns>An IPlaylistWriter instance.</returns> public static IPlaylistWriter CreateWriter( string key, string root, string name, bool createSubdirectories) { IPlaylistWriter writer = null; switch (key) { case "M3U": writer = new M3UPlaylistWriter(root, name, createSubdirectories); break; case "PLS": writer = new PLSPlaylistWriter(root, name, createSubdirectories); break; case "WPL": writer = new WPLPlaylistWriter(root, name, createSubdirectories); break; case "ZPL": writer = new ZPLPlaylistWriter(root, name, createSubdirectories); break; } return(writer); }
public void Export(string playlistType, bool excludeSmart, IPlaylistWriter playlistWriter) { var allPlaylists = GetAllPlaylistsOfType(playlistType, excludeSmart); var allPlaylistNames = allPlaylists.Select(xe => xe.Attribute("title")?.Value); Export(playlistType, allPlaylistNames, excludeSmart, playlistWriter); }
public void Export_CorrectInputs_Succeeds() { _playlistWriter = Substitute.For <IPlaylistWriter>(); PlaylistExporter sut = new PlaylistExporter(_fileSystem, _playlistReader, _playlistWriter); sut.Export(".\\TestData\\Laptop.m3u", "C:\\temp\\output", "C:\\Users\\jfox\\Music\\iTunes\\iTunes Media\\Music", ExportMode.PlaylistContents); }
public void Export_PlaylistOnly_Succeeds() { _playlistWriter = new PlaylistWriter( new SensusPlaylistFormatter(_fileSystem)); PlaylistExporter sut = new PlaylistExporter(_fileSystem, _playlistReader, _playlistWriter); sut.Export(".\\TestData\\Laptop.m3u", "C:\\temp\\output", "C:\\Users\\jfox\\Music\\iTunes\\iTunes Media\\Music", ExportMode.PlaylistFile); }
/// <summary> /// Initialize the environment for an export or synchronize operation. /// </summary> private void Initialize() { Logger.WriteLine(base.name, String.Format("Export beginning, using encoder '{0}'", encoder == null ? "(skip)" : encoder.Name)); // attach COM status handlers base.EnableInterrupt(controller); // override current encoder if different than requested if ((encoder != null) && !encoder.IsEmpty) { if (!controller.CurrentEncoder.Name.Equals(encoder.Name)) { // remember user's preferred encoder saveEncoder = controller.CurrentEncoder; // set the temporary encoder for this playlist controller.CurrentEncoder = encoder; } } // ensure that 'location' exists before continuing. This will be more efficient // for cases that do not require further subdirectories but also sets the stage... if (!Directory.Exists(location)) { if (ScannerBase.isLive) { Directory.CreateDirectory(location); } } // if we do want subdirectories then ensure we can create them if (!createSubdirectories) { createSubdirectories = EnsureFolderCapability(); } // initialize and open the playlist writer if a playlist is requested if (ScannerBase.isLive && !playlistFormat.Equals(PlaylistProviderFactory.NoFormat)) { writer = PlaylistProviderFactory.CreateWriter( playlistFormat, location, exportPIDs.Name, createSubdirectories); } // this ManualResetEvent is used to synchronize sequential processing of iTunes // tracks as they are encoded. iTunes encoding is an asynchronous procedure // however, iTunes does not allow concurrent encodings to occur. reset = new ManualResetEvent(false); exports = new StringCollection(); }
/// <summary> /// Cleanup anything started in Initialize. /// </summary> private void Cleanup() { // detach COM status handlers base.DisableInterrupt(controller); if (saveEncoder != null) { try { // restore the iTunes encoder as specified in the user Preferences controller.CurrentEncoder = saveEncoder; } catch { // no-op } } if (encoder != null) { encoder.Dispose(true); encoder = null; } if (writer != null) { writer.Close(); writer.Dispose(); writer = null; } if (exports != null) { exports.Clear(); exports = null; } if (reset != null) { reset.Dispose(); reset = null; } base.ProgressPercentage = 100; base.UpdateProgress(Resx.Completed); Logger.WriteLine(base.name, "Export completed"); }
public PlaylistExporter(IFileSystem fileSystem, IPlaylistReader playlistReader, IPlaylistWriter playlistWriter) { if (fileSystem == null) { throw new ArgumentNullException(nameof(fileSystem)); } if (playlistReader == null) { throw new ArgumentNullException(nameof(playlistReader)); } if (playlistWriter == null) { throw new ArgumentNullException(nameof(playlistWriter)); } _fileSystem = fileSystem; _playlistReader = playlistReader; _playlistWriter = playlistWriter; }
public MainWindow() { _audioDeviceLocater = new AudioDeviceLocater(); //Load app configuration string configFilename = System.IO.Path.Join(AppContext.BaseDirectory, CONFIG_FILENAME); ConfigurationLoader configLoader = new ConfigurationLoader(); configLoader.LoadFromFile(configFilename); _config = configLoader.Configuration; //Get list of Music search locations List <string> searchLocations = new List <string>(); searchLocations.Add(System.IO.Path.Join(AppContext.BaseDirectory, "Music")); searchLocations.AddRange(_config.SearchLocations); _fileLocater = new LocalTrackLocater(searchLocations.ToArray()); //Instantiate requires classes _metadataExtractor = new MetadataExtractor(); _localLibraryManager = new LocalLibraryManager(_fileLocater, _metadataExtractor); _musicPlayer = new MusicPlayer(); _queueBuilder = new QueueBuilder(); _playlistReader = new LocalPlaylistReader(_localLibraryManager, System.IO.Path.Join(AppContext.BaseDirectory, "Playlists")); _playlistWriter = new LocalPlaylistWriter(System.IO.Path.Join(AppContext.BaseDirectory, "Playlists")); _playlistManager = new PlaylistManager(_playlistReader, _playlistWriter); _trackProgressTimer = new DispatcherTimer(); _trackProgressTimer.Interval = TimeSpan.FromSeconds(0.5); _trackProgressTimer.Tick += (_, __) => { lblCurrentTime.Content = _musicPlayer.GetCurrentTrackTimePosition().ToString(@"mm\:ss"); }; //Initialise the search page _searchPage = new TrackPage(); InitializeComponent(); }
//======================================================================================== // Constructor //======================================================================================== /// <summary> /// Initialize a new instance of this scanner. /// </summary> /// <param name="controller">The iTunesAppClass to use.</param> /// <param name="catalog"></param> /// <param name="exportPIDs"> /// The list of persistent track IDs. When exporting multiple playlists, this list /// should include all tracks from all playlists where each track indicates its own /// source playlist. This allows comprehensive/overall feedback for UI progress bars. /// </param> /// <param name="encoder">The encoder to use to convert tracks.</param> /// <param name="playlistFormat"> /// The playlist output format or PlaylistProviderFactory.NoFormat for no playlist file. /// </param> /// <param name="location"> /// The target root directory path to which all entries will be copied or converted. /// </param> /// <param name="pathFormat"> /// The path format string as specified in FolderFormts.xml or null for title only. /// </param> /// <param name="isSynchronized"> /// True if target location should be synchronized, removing entries in the target /// location that are not included in the exportPIDs collection. /// </param> public ExportScanner( Controller controller, ICatalog catalog, PersistentIDCollection exportPIDs, Encoder encoder, string playlistFormat, string location, string pathFormat, bool isSynchronized) : base(Resx.I_ScanExport, controller, catalog) { base.description = isSynchronized ? Resx.ScanSynchronize : Resx.ScanExport; base.tooltip = String.Format(Resx.ExportingCount, exportPIDs.Count); this.exportPIDs = exportPIDs; this.encoder = encoder; this.expectedType = (encoder == null ? String.Empty : encoder.ExpectedType); this.playlistFormat = playlistFormat; this.playlistName = exportPIDs.Name; this.location = location; this.createSubdirectories = (pathFormat != null); this.pathFormat = pathFormat ?? PathHelper.GetPathFormat(FlatPathFormat); this.isSynchronized = isSynchronized; this.exports = null; this.writer = null; }
/// <summary> /// Cleanup anything started in Initialize. /// </summary> private void Cleanup() { // detach COM status handlers controller.DisabledEvent -= disabledHandler; controller.EnabledEvent -= enabledHandler; if (saveEncoder != null) { try { // restore the iTunes encoder as specified in the user Preferences controller.CurrentEncoder = saveEncoder; } catch { // no-op } } if (encoder != null) { encoder.Dispose(true); encoder = null; } if (writer != null) { writer.Close(); writer.Dispose(); writer = null; } if (exports != null) { exports.Clear(); exports = null; } reset = null; base.ProgressPercentage = 100; UpdateProgress(Resx.Completed); Logger.WriteLine(base.name, "Export completed"); }
public void Export(string playlistType, string playlistName, bool excludeSmart, IPlaylistWriter playlistWriter) { Export(playlistType, new[] { playlistName }, excludeSmart, playlistWriter); }
public void Export(string playlistType, IEnumerable <string> playlistNames, bool excludeSmart, IPlaylistWriter playlistWriter) { var allPlaylists = GetAllPlaylistsOfType(playlistType, excludeSmart); var playlistElements = allPlaylists.Where(xe => playlistNames.Contains(xe.Attribute("title")?.Value)).ToList(); if (playlistElements.Count <= 0) { throw new PlaylistExportException($"No playlists of type '{playlistType}' with the specified name(s) were found."); } foreach (var playlistElement in playlistElements) { var mediaContainerElement = GetMediaContainer(playlistElement); playlistWriter.Write(mediaContainerElement); } }
public void AddWriter(IPlaylistWriter writer) { Writers.Add(writer.Id, writer); }
public PlaylistManager(IPlaylistReader PlaylistReader, IPlaylistWriter PlaylistWriter) { _playlistReader = PlaylistReader; _playlistWriter = PlaylistWriter; }
/// <summary> /// Initialize the environment for an export or synchronize operation. /// </summary> private void Initialize() { Logger.WriteLine(base.name, String.Format("Export beginning, using encoder '{0}'", encoder.Name)); // attach COM status handlers disabledHandler = new InteractionDisabledHandler(DoCOMCallsDisabled); enabledHandler = new InteractionEnabledHandler(DoCOMCallsEnabled); controller.DisabledEvent += disabledHandler; controller.EnabledEvent += enabledHandler; // override current encoder if different than requested if (!encoder.IsEmpty) { if (!controller.CurrentEncoder.Name.Equals(encoder.Name)) { // remember user's preferred encoder saveEncoder = controller.CurrentEncoder; // set the temporary encoder for this playlist controller.CurrentEncoder = encoder; } } // ensure that 'location' exists before continuing. This will be more efficient // for cases that do not require further subdirectories but also sets the stage... if (!Directory.Exists(location)) { if (ScannerBase.isLive) { Directory.CreateDirectory(location); } } // if we do want subdirectories then ensure we can create them if (!createSubdirectories) { createSubdirectories = EnsureFolderCapability(); } // initialize and open the playlist writer if a playlist is requested if (ScannerBase.isLive && !playlistFormat.Equals(PlaylistFactory.NoFormat)) { writer = PlaylistFactory.CreateWriter( playlistFormat, location, exportPIDs.Name, createSubdirectories); writer.Open(); } // this ManualResetEvent is used to synchronize sequential processing of iTunes // tracks as they are encoded. iTunes encoding is an asynchronous procedure // however, iTunes does not allow concurrent encodings to occur. waitSyncRoot = null; reset = new ManualResetEvent(false); exports = new StringCollection(); }
private IPlaylistWriter writer; // playlist writer #endregion Fields #region Constructors //======================================================================================== // Constructor //======================================================================================== /// <summary> /// Initialize a new instance of this scanner. /// </summary> /// <param name="itunes">The iTunesAppClass to use.</param> /// <param name="exportPIDs"> /// The list of persistent track IDs. When exporting multiple playlists, this list /// should include all tracks from all playlists where each track indicates its own /// source playlist. This allows comprehensive/overall feedback for UI progress bars. /// </param> /// <param name="encoder">The encoder to use to convert tracks.</param> /// <param name="playlistFormat"> /// The playlist output format or PlaylistFactory.NoFormat for no playlist file. /// </param> /// <param name="location"> /// The target root directory path to which all entries will be copied or converted. /// </param> /// <param name="pathFormat"> /// The path format string as specified in FolderFormts.xml or null for title only. /// </param> /// <param name="isSynchronized"> /// True if target location should be synchronized, removing entries in the target /// location that are not included in the exportPIDs collection. /// </param> public ExportScanner( Controller controller, PersistentIDCollection exportPIDs, Encoder encoder, string playlistFormat, string location, string pathFormat, bool isSynchronized) { base.name = Resx.I_ScanExport; base.description = isSynchronized ? Resx.ScanSynchronize : Resx.ScanExport; base.controller = controller; this.exportPIDs = exportPIDs; this.encoder = encoder; this.expectedType = encoder.ExpectedType; this.playlistFormat = playlistFormat; this.playlistName = exportPIDs.Name; this.location = location; this.createSubdirectories = (pathFormat != null); this.pathFormat = pathFormat ?? PathHelper.GetPathFormat(FlatPathFormat); this.isSynchronized = isSynchronized; this.exports = null; this.writer = null; this.slim = new ReaderWriterLockSlim(); this.waitSyncRoot = null; }
public PlaylistExporterTest() { _fileSystem = Substitute.For <IFileSystem>(); _playlistReader = Substitute.For <IPlaylistReader>(); _playlistWriter = Substitute.For <IPlaylistWriter>(); }