AVURLAsset trackingWithMediaType 在模拟器中不返回 AVMediaTypeAudio 的音频轨道

Mar*_*tek 2 objective-c ios avasset

我正在做以下事情

    AVURLAsset              *audioAsset  = [[AVURLAsset alloc] initWithURL:audioUrl options:nil];
    NSArray<AVAssetTrack *> *audioTracks = [audioAsset tracksWithMediaType:AVMediaTypeAudio];
Run Code Online (Sandbox Code Playgroud)

在真实设备上运行良好。

问题只发生在模拟器中。我在捆绑包中静态添加了 mp3,因此audioAsset已正确启动。但是audioTracks模拟器上的数组是空的(即使路径audioUrlaudioAsset变量是正确的并且存在。

有什么建议?

小智 5

我在真实设备上也遇到过同样的问题。该问题是由于初始化资产后尚未准备好这一事实引起的。

请看一下文档

您可以使用现有资产初始化播放器项目,也可以直接从 URL 初始化播放器项目,以便您可以在特定位置播放资源(然后 AVPlayerItem 将为资源创建和配置资产)。但是,与 AVAsset 一样,简单地初始化播放器项目并不一定意味着它可以立即播放。您可以观察(使用键值观察)项目的状态属性,以确定它是否以及何时可以播放。

要解决此问题,您可以尝试执行以下操作:

AVURLAsset *audioAsset = [[AVURLAsset alloc] initWithURL:audioUrl options:nil];
NSString *tracksKey = @"tracks";
[audioAsset loadValuesAsynchronouslyForKeys:@[tracksKey] completionHandler:
 ^{
    NSError *error;
    AVKeyValueStatus status = [asset statusOfValueForKey:tracksKey error:&error];
    if (status == AVKeyValueStatusLoaded) { 
        // The asset is ready at this point
        NSArray<AVAssetTrack *> *audioTracks = [audioAsset tracksWithMediaType:AVMediaTypeAudio];
     }
 }];
Run Code Online (Sandbox Code Playgroud)

另外值得注意的是,如果 audioAsset 不可播放,则 AVKeyValueStatus 状态可以是 AVKeyValueStatusFailed:

BOOL result = [audioAsset isPlayable];
Run Code Online (Sandbox Code Playgroud)