歌曲更改时如何更新 MPMusicPlayerController

Posted

技术标签:

【中文标题】歌曲更改时如何更新 MPMusicPlayerController【英文标题】:How to update MPMusicPlayerController when song changes 【发布时间】:2015-06-05 05:46:49 【问题描述】:

我想知道当 MPMusicPlayerController 中的歌曲发生变化时你会更新 UI。例如,如果您有一个带有专辑封面的图像视图,但用户按下了跳过按钮,您将如何使用新的专辑封面更新图像视图的图像?

【问题讨论】:

【参考方案1】:

为了控制音乐播放,我们使用 MPMusicPlayerController 的实例。有两种类型的音乐播放器。 iPodMusicPlayer 是对 iPod 应用程序使用的音乐播放器实例的引用。您更改的任何设置,例如随机播放或重复模式,也会在 iPod 应用程序中更改。如果您的应用程序启动时 iPod 正在播放,则音乐将继续播放,您可以访问当前歌曲并在当前活动的播放列表中前后跳动。当您的应用退出时,音乐将继续播放。我想这种模式对于大多数试图通过与 iPod 交互来改善你的音乐聆听体验的实用应用程序来说非常方便。 相比之下,applicationMusicPlayer 为您提供了一个音乐播放器,您可以独立于 iPod 应用程序更改其设置。如果您的应用是一款游戏,并且您想让用户能够从他们的音乐库中选择背景音乐,这可能就是您要走的路。在 Songtext 中,我们将使用 iPodMusicPlayer,因为我们想知道当我们的应用启动时正在播放哪首歌:

@property (nonatomic, strong) MPMusicPlayerController *musicPlayer;
self.musicPlayer = [MPMusicPlayerController iPodMusicPlayer];

音乐播放器使用通知来通知您有关以下内容的更改: - 当前歌曲(MPMusicPlayerControllerNowPlayingItemDidChangeNotification), - 播放/暂停/停止状态 (MPMusicPlayerControllerPlaybackStateDidChangeNotification),或 - 音量 (MPMusicPlayerControllerVolumeDidChangeNotification)。 因此,您通常要做的下一件事是将自己注册为您感兴趣的通知的观察者,例如在 viewDidLoad 中。我们希望收到所有 3 条通知:

// Register for music player notifications
NSNotificationCenter *notificationCenter = [NSNotificationCenter   defaultCenter];
[notificationCenter addObserver:self 
                   selector:@selector(handleNowPlayingItemChanged:)
                        name:MPMusicPlayerControllerNowPlayingItemDidChangeNotification 
                     object:self.musicPlayer];
[notificationCenter addObserver:self 
                   selector:@selector(handlePlaybackStateChanged:)
                       name:MPMusicPlayerControllerPlaybackStateDidChangeNotification 
                     object:self.musicPlayer];
[notificationCenter addObserver:self 
                   selector:@selector(handleExternalVolumeChanged:)
                        name:MPMusicPlayerControllerVolumeDidChangeNotification 
                     object:self.musicPlayer];
[self.musicPlayer beginGeneratingPlaybackNotifications];

当媒体库的内容发生变化时,iPod 媒体库会发送另一个相关通知,例如当您将设备与 iTunes 同步时。如果您的应用创建了需要在库更改后更新的播放列表,您必须收听此通知。为此,请将自己注册为 MPMediaLibraryDidChangeNotification 通知的观察者并调用:

[[MPMediaLibrary defaultMediaLibrary] beginGeneratingLibraryChangeNotifications]

通知处理程序是您更新 UI 以响应玩家状态变化的地方:

// 当正在播放的项目发生变化时,更新歌曲信息标签和艺术品显示。 - (void)handleNowPlayingItemChanged:(id)notification // 向音乐播放器询问当前歌曲。 MPMediaItem *currentItem = self.musicPlayer.nowPlayingItem;

// Display the artist, album, and song name for the now-playing media item.
// These are all UILabels.
self.songLabel.text   = [currentItem valueForProperty:MPMediaItemPropertyTitle];
self.artistLabel.text = [currentItem valueForProperty:MPMediaItemPropertyArtist];
self.albumLabel.text  = [currentItem valueForProperty:MPMediaItemPropertyAlbumTitle];    

// Display album artwork. self.artworkImageView is a UIImageView.
CGSize artworkImageViewSize = self.artworkImageView.bounds.size;
MPMediaItemArtwork *artwork = [currentItem valueForProperty:MPMediaItemPropertyArtwork];
if (artwork != nil) 
    self.artworkImageView.image = [artwork imageWithSize:artworkImageViewSize];
 else 
    self.artworkImageView.image = nil;

// When the playback state changes, set the play/pause button appropriately.
- (void)handlePlaybackStateChanged:(id)notification 
MPMusicPlaybackState playbackState = self.musicPlayer.playbackState;
if (playbackState == MPMusicPlaybackStatePaused || playbackState == MPMusicPlaybackStateStopped) 
    [self.playPauseButton setTitle:@"Play" forState:UIControlStateNormal];
 else if (playbackState == MPMusicPlaybackStatePlaying) 
    [self.playPauseButton setTitle:@"Pause" forState:UIControlStateNormal];

// When the volume changes, sync the volume slider
- (void)handleExternalVolumeChanged:(id)notification 
// self.volumeSlider is a UISlider used to display music volume.
// self.musicPlayer.volume ranges from 0.0 to 1.0.
[self.volumeSlider setValue:self.musicPlayer.volume animated:YES];

【讨论】:

【参考方案2】:

如果您正在寻找锁屏播放信息:

看看MPNowPlayingInfoCenter

你需要传递一个NSDictionary,这是一个例子:

-(void)updateNowPlayingInfo

    //Set Values for MPNowPlayingInfoCenter
    NSArray *keys = [NSArray arrayWithObjects:
                     MPMediaItemPropertyTitle,
                     MPMediaItemPropertyPlaybackDuration,
                     MPNowPlayingInfoPropertyPlaybackRate,
                     MPNowPlayingInfoPropertyElapsedPlaybackTime,
                     nil];

    NSArray *values = [NSArray arrayWithObjects:
                       self.currentPlayingVideo.title,
                       [NSNumber numberWithFloat:self.currentPlayingVideo.duration],
                       [NSNumber numberWithInt:1],
                       [NSNumber numberWithDouble:self.currentVideoPlayView.videoPlayerViewController.moviePlayer.currentPlaybackTime],
                       nil];

    NSDictionary *mediaInfo = [NSDictionary dictionaryWithObjects:values forKeys:keys];
    [[MPNowPlayingInfoCenter defaultCenter] setNowPlayingInfo:mediaInfo];

【讨论】:

以上是关于歌曲更改时如何更新 MPMusicPlayerController的主要内容,如果未能解决你的问题,请参考以下文章

如何知道用户何时使用 Spotify API 更改歌曲

如何使用方法更改按钮的 on_release 功能?

如何更改锁定屏幕/控制中心的轨道位置?

当我停止使用功能播放歌曲并更改导航栏索引时,颤动的音乐继续播放

如何将歌曲/目录添加到 Python MPD 播放列表

将歌曲信息从 iTunes 同步到 Android 手机时出现问题