// // Track.swift // Tag for iTunes // // Created by Kim Wittenburg on 30.05.15. // Copyright (c) 2015 Kim Wittenburg. All rights reserved. // import Cocoa /// Represents a track of the /// [Search API](https://www.apple.com/itunes/affiliates/resources/documentation/itunes-store-web-service-search-api.html). public class Track: iTunesType { // MARK: Properties public let id: iTunesId public let name: String public let censoredName: String public let artistName: String public let releaseDate: NSDate public let trackNumber: Int public let trackCount: Int public let discNumber: Int public let discCount: Int public let genre: String public internal(set) weak var album: Album! /// These tracks will be changed, if `save()` is called. public var associatedTracks = [iTunesTrack]() // MARK: Initializers public required init(data: [iTunesAPI.Field: AnyObject]) { id = data[.TrackId] as! UInt name = data[.TrackName] as! String censoredName = data[.TrackCensoredName] as! String artistName = data[.ArtistName] as! String releaseDate = iTunesAPI.sharedDateFormatter.dateFromString(data[.ReleaseDate] as! String)! trackNumber = data[.TrackNumber] as! Int trackCount = data[.TrackCount] as! Int discNumber = data[.DiscNumber] as! Int discCount = data[.DiscCount] as! Int genre = data[.PrimaryGenreName] as! String } public static var requiredFields: [iTunesAPI.Field] { return [.TrackId, .TrackName, .TrackCensoredName, .ArtistName, .ReleaseDate, .TrackNumber, .TrackCount, .DiscNumber, .DiscCount, .PrimaryGenreName] } // MARK: Methods /// Saves the track. This means that its properties are applied to every /// `iTunesTrack` in its `associatedTracks`. /// /// This method respects the user's preferences (See `Preferences` class). public func save() { saveToTracks(associatedTracks) } /// Applies the receiver's properties to the specified tracks. /// /// This method respects the user's preferences (See `Preferences` class). public func saveToTracks(tracks: [iTunesTrack]) { for track in tracks { saveToTrack(track) } } /// Applies the receiver's properties to the specified `track`. /// /// This method respects the user's preferences (See `Preferences` class). public func saveToTrack(track: iTunesTrack) { let components = NSCalendar.currentCalendar().components(.Year, fromDate: releaseDate) track.name = name track.artist = artistName track.year = components.year track.trackNumber = trackNumber track.trackCount = trackCount track.discNumber = discNumber track.discCount = discCount track.genre = genre track.album = album?.name track.albumArtist = album?.artistName track.sortName = "" track.sortAlbum = "" track.sortAlbumArtist = "" track.sortArtist = "" track.composer = "" track.sortComposer = "" track.comment = "" track.artworks().removeAllObjects() } /// Returns `true` if all `associatedTrack`s contain the same values as the /// `Track` instance. public var saved: Bool { let components = NSCalendar.currentCalendar().components(.Year, fromDate: releaseDate) for track in associatedTracks { guard track.name == name && track.artist == artistName && track.year == components.year && track.trackNumber == trackNumber && track.trackCount == trackCount && track.discNumber == discNumber && track.discCount == discCount && track.genre == genre && track.album == album.name && track.albumArtist == album.artistName && track.composer == "" else { return false } } return true } } extension Track: Hashable { public var hashValue: Int { return Int(id) } } public func ==(lhs: Track, rhs: Track) -> Bool { return lhs.id == rhs.id }