Ios MP3队列播放器-在后台线程中加载?
我有一个Ios MP3队列播放器-在后台线程中加载?,ios,objective-c,audio,avplayer,avqueueplayer,Ios,Objective C,Audio,Avplayer,Avqueueplayer,我有一个AVQueuePlayer,用于播放来自互联网(http)的MP3歌曲列表。我还需要知道目前正在播放哪首歌。当前的问题是加载歌曲会导致延迟,在等待歌曲加载时会阻塞主线程(第一首歌曲以及第一首歌曲完成播放后的连续歌曲) 以下代码阻止主线程: queuePlayer = [[AVQueuePlayer alloc] init]; [queuePlayer insertItem: [AVPlayerItem playerItemWithURL:url] afterItem: nil]; //
AVQueuePlayer
,用于播放来自互联网(http)的MP3歌曲列表。我还需要知道目前正在播放哪首歌。当前的问题是加载歌曲会导致延迟,在等待歌曲加载时会阻塞主线程(第一首歌曲以及第一首歌曲完成播放后的连续歌曲)
以下代码阻止主线程:
queuePlayer = [[AVQueuePlayer alloc] init];
[queuePlayer insertItem: [AVPlayerItem playerItemWithURL:url] afterItem: nil]; // etc.
[queuePlayer play]
我正在寻找一种创建MP3播放列表的方法,其中下一个要播放的文件将在后台预加载。
我尝试了以下代码:
NSArray* tracks = [NSArray arrayWithObjects:@"http://example.com/song1.mp3", @"http://example.com/song2.mp3", @"http://example.com/song3.mp3", nil];
for (NSString* trackName in tracks)
{
AVURLAsset* audioAsset = [[AVURLAsset alloc]initWithURL:[NSURL URLWithString:trackName]
options:nil];
AVMutableCompositionTrack* audioTrack = [_composition addMutableTrackWithMediaType:AVMediaTypeAudio
preferredTrackID:kCMPersistentTrackID_Invalid];
NSError* error;
[audioTrack insertTimeRange:CMTimeRangeMake([_composition duration], audioAsset.duration)
ofTrack:[[audioAsset tracksWithMediaType:AVMediaTypeAudio]objectAtIndex:0]
atTime:kCMTimeZero
error:&error];
if (error)
{
NSLog(@"%@", [error localizedDescription]);
}
// Store the track IDs as track name -> track ID
[_audioMixTrackIDs setValue:[NSNumber numberWithInteger:audioTrack.trackID]
forKey:trackName];
}
_player = [[AVPlayer alloc] initWithPlayerItem:playerItem];
[_player play];
问题是我不确定如何检测下一首歌曲何时开始播放。此外,文档没有指定这是否会预加载MP3文件
我正在寻找一种解决方案:
- 通过在播放前在后台预加载MP3来播放MP3(理想情况下,在当前歌曲结束前开始加载下一首歌曲,以便在当前歌曲结束后立即播放)
- 允许我查看当前播放的歌曲
AVPlayerItem
。更好的解决方案是创建一个AVQueuePlayer
,其中包含要播放的AVPlayerItem
对象数组
NSArray* tracks = [NSArray arrayWithObjects:@"http://example.com/song1.mp3", @"http://example.com/song2.mp3", @"http://example.com/song3.mp3", nil];
NSMutableArray *playerItems = [[NSMutableArray alloc] init];
for (NSString* trackName in tracks)
{
NSURL *assetURL = [NSURL URLWithString:trackName];
if (!assetURL) {
continue;
}
AVURLAsset* audioAsset = [[AVURLAsset alloc] initWithURL:assetURL
options:nil];
AVPlayerItem *playerItem = [[AVPlayerItem alloc] initWithAsset:audioAsset];
[playerItems addObject:playerItem];
}
_player = [[AVQueuePlayer alloc] initWithItems:playerItems];
[_player play];
在回答您的最后总结问题时:
- 是,
在播放当前项目时,会预加载播放列表中的下一个项目AVQueuePlayer
- 您可以访问
属性来确定当前正在播放的currentItem
AVPlayerItem