Search code examples
iphoneioscore-audioavaudioplayer

AVAudioPlayer doesn't play audio in once in 15 times


I'm facing a really strange issue with AVAudioPlayer. I have initialised the AVAudioPlayer as given below. It plays audio most of the time, but no audio plays once every 15-20 times. The player is getting initialised properly and there are no error. Please help me fix the issue.

AVAudioPlayer *backgroundMusicPlayer = [[AVAudioPlayer alloc] initWithContentsOfURL:backgroundMusicURL error:&error];
self.backgroundMusicPlayer = backgroundMusicPlayer;
[backgroundMusicPlayer release];
[self.backgroundMusicPlayer setDelegate:self];
[self.backgroundMusicPlayer prepareToPlay];
[self.backgroundMusicPlayer play];

Solution

  • Use GCD to load audio data. using GCD to asynchronously load the song's data into an instance of NSData and use that as a feed to audio player. you have to do this because loading the data of an audio file, depending on the length of the audio file, can take a long time and if you are doing this on the main thread, then you are running the risk of stalling the UI experience. Because of this, you have to use global concurrent queue to ensure that your code does not run on the main thread.if it is on the main thread then problem like you are facing happens. see this sample code

         dispatch_queue_t dispatchQueue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
            dispatch_async(dispatchQueue, ^(void)
         { 
        NSBundle *mainBundle = [NSBundle mainBundle];
            NSString *filePath = [mainBundle pathForResource:@"MySong" ofType:@"mp3"];
            NSData *fileData = [NSData dataWithContentsOfFile:filePath]; NSError *audioPlayerError = nil;
         self.audioPlayer = [[AVAudioPlayer alloc] initWithData:fileData error:&audioPlayerError];
    
            if (self.audioPlayer != nil)
        {
            self.audioPlayer.delegate = self;
            if ([self.audioPlayer prepareToPlay] && [self.audioPlayer play])
        {
            NSLog(@"Successfully started playing.");
            } 
        else 
        { 
        NSLog(@"Failed to play the audio file.");
         self.audioPlayer = nil;
            }
            } 
        else { NSLog(@"Could not instantiate the audio player.");
    } });
    

    your problem also may be happen because of initWithContentsOfURL, if it not gets data through that URL then it not plays audio.

    Other issue with your code is may be releasing the audioPlayer object. If you are allocating a lot of objects and never releasing them from memory. That could eventually lead to a low memory .