Search code examples
iosflutteraudio-player

flutter audio player play sound not working in IOS


I am using flutter plugin audioplayers: ^0.7.8, the below code is working in Android but not working in IOS. I run the code in real ios device and click the button. It suppose the play the mp3 file, but no sound at all. Please help to solve this issue.

I already set up the info.plist

<key>NSAppTransportSecurity</key>
<dict>
    <key>NSAllowsArbitraryLoads</key>
    <true/>
</dict>

Here with the print out from the console:

  • flutter: finished loading, uri=file:///var/mobile/Containers/Data/Application/E3A576E2-0F21-44CF-AF99-319D539767D0/Library/Caches/demo.mp3
  • Syncing files to device iPhone...
  • flutter: _platformCallHandler call audio.onCurrentPosition {playerId: 273e1d27-b6e8-4516-bb3f-967a41dff308, value: 0}
  • flutter: _platformCallHandler call audio.onError {playerId: 273e1d27-b6e8-4516-bb3f-967a41dff308, value: AVPlayerItemStatus.failed}

Here with my code:

class _MyHomePageState extends State<MyHomePage> {
  AudioPlayer audioPlugin = AudioPlayer();
  String mp3Uri;

  @override
  void initState() {
    AudioPlayer.logEnabled = true;
    _load();
  }

  Future<Null> _load() async {
    final ByteData data = await rootBundle.load('assets/demo.mp3');
    Directory tempDir = await getTemporaryDirectory();
    File tempFile = File('${tempDir.path}/demo.mp3');
    await tempFile.writeAsBytes(data.buffer.asUint8List(), flush: true);
    mp3Uri = tempFile.uri.toString();
    print('finished loading, uri=$mp3Uri');
  }

  void _playSound() {
    if (mp3Uri != null) {
      audioPlugin.play(mp3Uri, isLocal: true,
      );
    }
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: const Text('Audio Player Demo Home Page'),
      ),
      body: Center(),
      floatingActionButton: FloatingActionButton(
        onPressed: _playSound,
        tooltip: 'Play',
        child: const Icon(Icons.play_arrow),
      ),
    );
  }
}

Solution

  • If you want to use a local file, you have to use AudioCache.

    Looking at the documentation, it says at the bottom:

    AudioCache

    In order to play Local Assets, you must use the AudioCache class.

    Flutter does not provide an easy way to play audio on your assets, but this class helps a lot. It actually copies the asset to a temporary folder in the device, where it is then played as a Local File.

    It works as a cache because it keep track of the copied files so that you can replay then without delay.

    To get audio to play, this is what I figured out what we need to do:

    import 'package:flutter/material.dart';
    import 'package:audioplayers/audio_cache.dart';
    
    AudioCache audioPlayer = AudioCache();
    
    void main() {
      runApp(new MyApp());
    }
    
    
    
    
    class MyApp extends StatefulWidget {
      @override _MyAppState createState() => _MyAppState();
    }
    
    class _MyAppState extends State<MyApp> {
      @override initState(){
        super.initState();
        audioPlayer.play("Jingle_Bells.mp3");
      }
      @override Widget build(BuildContext context) {
        //This we do not care about
      }
    }
    

    Important:

    It automatically places 'assets/' in front of your path. This means you if you wanted to load assets/Jingle_Bells.mp3, you would simply put audioPlayer.play("Jingle_Bells.mp3");. If you entered audioPlayer.play("assets/Jingle_Bells.mp3"); instead, AudioPlayers would actually load assets/assets/Jingle_Bells.mp3 instead.

    ``