Slow start for AVAudioPlayer the first time a sound is played

后端 未结 9 1335
孤城傲影
孤城傲影 2020-12-02 09:23

I\'m trying to eliminate startup lag when playing a (very short -- less than 2 seconds) audio file via AVAudioPlayer on the iPhone.

First, the code:

         


        
相关标签:
9条回答
  • 2020-12-02 10:00

    Here's a simple Swift extension to AVAudioPlayer that uses the play-and-stop at 0 volume idea presented in previous answers. PrepareToPlay() unfortunately at least for me did not do the trick.

    extension AVAudioPlayer {
        private func initDelaylessPlayback() {
            volume = 0
            play()
            stop()
            volume = 1
        }
    
        convenience init(contentsOfWithoutDelay : URL) throws {
            try self.init(contentsOf: contentsOfWithoutDelay, fileTypeHint: nil)
            initDelaylessPlayback()
        }
    }
    
    0 讨论(0)
  • 2020-12-02 10:06

    Here's what I've done (in a separate thread):

    [audioplayer start]
    [audioplayer stop]
    self.audioplayer = audioplayer
    

    [audioplayer prepareToPlay] seems to be an asynchronous method, so you can't be sure when it returns if the audio is in fact ready to play.

    In my case I call start to actually start playing - this appears to be synchronous. Then I stop it immediately. In the simulator anyway I don't hear any sound coming out from this activity. Now that the sound is "really" ready to play, I assign the local variable to a member variable so code outside the thread has access to it.

    I must say I find it somewhat surprising that even on iOS 4 it takes some 2 seconds just to load an audio file that is only 4 seconds in length....

    0 讨论(0)
  • 2020-12-02 10:07

    I've taken an alternative approach that works for me. I've seen this technique mentioned elsewhere (tho I don't recall at the moment where that was).

    In short, preflight the sound system by loading and playing a short, "blank" sound before you do anything else. The code looks like this for a short mp3 file I preload in my view controller'sviewDidLoad method that's of .1 second duration:

       NSError* error = nil;
       NSString* soundfilePath = [[NSBundle mainBundle] pathForResource:@"point1sec" ofType:@"mp3"];
       NSURL* soundfileURL = [NSURL fileURLWithPath:soundfilePath];
       AVAudioPlayer* player = [[[AVAudioPlayer alloc] initWithContentsOfURL:soundfileURL error:&error] autorelease];
       [player play];  
    

    You can create your own blank mp3 if you want, or do a google search on "blank mp3s" to find and download one already constructed by somebody else.

    0 讨论(0)
提交回复
热议问题