Ios 在MPMusicLayerController无序播放MPMediaItemCollection,但让用户选择第一项?

Ios 在MPMusicLayerController无序播放MPMediaItemCollection,但让用户选择第一项?,ios,avfoundation,mpmusicplayercontroller,mpmediaitem,mpmediaitemcollection,Ios,Avfoundation,Mpmusicplayercontroller,Mpmediaitem,Mpmediaitemcollection,我正在开发一个与iOS上的iPod音乐应用程序集成的应用程序。它显示不同的音乐分组(即MPMediaItemCollections),并允许用户使用[MPMusicLayerController iPodMusicLayer]在音乐应用程序中播放这些分组 我的问题是,我很难让我的应用程序和音乐应用程序之间的洗牌功能以相同的方式工作。当我播放一首歌时,我叫: MPMusicPlayerController* musicPlayer = [MPMusicPlayerController iPodMu

我正在开发一个与iOS上的iPod音乐应用程序集成的应用程序。它显示不同的音乐分组(即MPMediaItemCollections),并允许用户使用[MPMusicLayerController iPodMusicLayer]在音乐应用程序中播放这些分组

我的问题是,我很难让我的应用程序和音乐应用程序之间的洗牌功能以相同的方式工作。当我播放一首歌时,我叫:

MPMusicPlayerController* musicPlayer = [MPMusicPlayerController iPodMusicPlayer];
[musicPlayer stop];
MPMediaItemCollection* collection = [self.displayedContainerGroup getMediaItemCollection];
[musicPlayer setQueueWithItemCollection:collection];
[musicPlayer setNowPlayingItem:[container getMediaItem];
[musicPlayer play];
如果关闭“洗牌”,这将非常有效。如果用户选择一首歌曲(属于专辑的一部分),则会在音乐应用程序中播放专辑,并从指定的歌曲开始播放

但是,如果启用了shuffle,那么这似乎是在首先对歌曲进行shuffle,然后按照刚刚进行shuffle的顺序跳转到新的nowPlayingItem。问题是,除非nowPlayingItem按顺序排列到第一位,否则它不会播放专辑中的所有歌曲

MPMusicLayerController文档介绍了nowPlayingItem:“要指定播放应从播放队列中的特定媒体项开始,请在音乐播放器停止或暂停时将此属性设置为该项。”


所以,我想知道是否有一种方法可以让它在随机播放模式下工作——从专辑中的一首用户选择的歌曲开始,然后播放所有其他被随机播放的歌曲。或者我应该创建一个定制的MPMediaItemCollection并自己洗牌吗?

这似乎已经奏效了;我必须关闭shuffle,添加歌曲,切换到正在播放的项目,然后重新打开shuffle:

[musicPlayer stop];
BOOL shuffleWasOn = NO;
if (musicPlayer.shuffleMode != MPMusicShuffleModeOff)
{
     musicPlayer.shuffleMode = MPMusicShuffleModeOff;
     shuffleWasOn = YES;
}
[musicPlayer setQueueWithItemCollection:mediaItemCollectionIn];
[musicPlayer setNowPlayingItem:mediaItemIn];
if (shuffleWasOn)
     musicPlayer.shuffleMode = MPMusicShuffleModeSongs;

[musicPlayer play];

下面是一个Swift 4的实现。我已经将代码重组为两个函数,
stop()
play()
,它们也可以单独用于停止和播放

重要:一个重要的区别是,我发现在调用
musicPlayer.stop()之前有必要存储
shuffleMode
shuffleMode
有时在调用
musicPlayer.stop()
后会发生更改

let musicPlayer = MPMusicPlayerController.systemMusicPlayer
private var shuffleMode = MPMusicPlayerController.systemMusicPlayer.shuffleMode

private func stop() {
    shuffleMode = musicPlayer.shuffleMode
    musicPlayer.shuffleMode = MPMusicShuffleMode.off

    musicPlayer.stop()
}

private func play() {
    musicPlayer.shuffleMode = shuffleMode

    musicPlayer.prepareToPlay()
    musicPlayer.play()
}

func play(itemCollection: MPMediaItemCollection, startingAt index: Int) {
    stop()

    musicPlayer.setQueue(with: itemCollection)
    musicPlayer.nowPlayingItem = itemCollection.items[index]

    play()
}