如何使用AVAudioPlayerNode显示歌曲的当前时间和持续时间

6

我正在使用AVAudioPlayerNode制作音频播放器,并且可以使用一些效果(延迟,音调变换,速度变换等)播放歌曲,但是我卡在了显示歌曲当前时间和持续时间上。

AVAudioPlayerNode似乎没有像AVAudioPlayer.currentTime或.duration这样的功能。

如果您能帮助我使用AVAudioPlayerNode显示当前时间和持续时间,我将不胜感激。

6个回答

14

目前,这就是我使用的:

- (NSTimeInterval)currentTimeInSeconds
{
    AVAudioTime *nodeTime = self.playerNode.lastRenderTime;
    AVAudioTime *playerTime = [self.playerNode playerTimeForNodeTime:nodeTime];

    NSTimeInterval seconds = (double)playerTime.sampleTime / playerTime.sampleRate; 
    return seconds;
}

除了以抽象时间为基础的渲染时间之外,播放节点通过playerTimeForNodeTime将此时间转换为自己的播放时间表。还会考虑暂停等因素。

此句话已翻译完毕,请确认是否还有其他需要翻译的内容。


1
@KeitaBickOhshiro 如果这个解决方案对您有效,您可以将其标记为正确答案或点赞以使其他成员看到它。 - Thorsten Karrer
2
这会给出实际的位置,但如果你使用AudioNode.ScheduleSegment(...),位置将不会被重置为0,它只是继续计数。 - DirtyNative
怎么解决这个问题,@DanielDirtyNativeMartin,请回复。 - Arpit B Parekh

8

以下是Swift的代码:

private func currentTime() -> NSTimeInterval {
    if let nodeTime: AVAudioTime = myAvAudioPlayer.lastRenderTime, playerTime: AVAudioTime = myAvAudioPlayer.playerTimeForNodeTime(nodeTime) {
       return Double(Double(playerTime.sampleTime) / playerTime.sampleRate)
    }
    return 0
}

只需将myAvAudioPlayer替换为您的AVAudioPlayerNode即可!

愉快编码!


1
只有在节点正在播放时,它才能正常工作。如果停止了,它会返回零。 - dmann200

6

Swift 5:

持续时间,使用AVAudioPlayerNodeAVAudioFile

extension AVAudioFile{

    var duration: TimeInterval{
        let sampleRateSong = Double(processingFormat.sampleRate)
        let lengthSongSeconds = Double(length) / sampleRateSong
        return lengthSongSeconds
    }

}

根据WWDC 2014:核心音频的新变化,54分钟所述。

然后是当前时间:

extension AVAudioPlayerNode{

    var current: TimeInterval{
        if let nodeTime = lastRenderTime,let playerTime = playerTime(forNodeTime: nodeTime) {
            return Double(playerTime.sampleTime) / playerTime.sampleRate
        }
        return 0
    }
}

感谢 @Brian Becker


5

AVAudioPlayerNode 持续的时间内 SWIFT 4:

func durationOfNodePlayer(_ fileUrl: URL) -> TimeInterval {
    do {

        let file = try AVAudioFile(forReading: fileUrl)
        let audioNodeFileLength = AVAudioFrameCount(file.length)
        return Double(Double(audioNodeFileLength) / 44100) //Divide by the AVSampleRateKey in the recorder settings

       } catch {

          return 0
       }

}

3

在这个过程中,AVAudioFile.length属性可用。我将文件中的采样帧数除以采样率(44100hz)。

对于当前时间,我暂时使用UISlider.value并将其与采样帧合成。


0

类似这样的代码应该可以让你实现这个功能...

extension AVAudioPlayerNode {
    var currentTime: TimeInterval {
    get {
        if let nodeTime: AVAudioTime = self.lastRenderTime, let playerTime: AVAudioTime = self.playerTime(forNodeTime: nodeTime) {
            return Double(playerTime.sampleTime) / playerTime.sampleRate
        }
        return 0
    }
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接