Search code examples
flutteraudiosignal-processingpcm

How is flutter sound stream representing pcm data?


I need to make a app that visualizes audio data by graphing it, and I've tried fluter sound and sound stream to get the raw audio data. However both of these libraries captures the sound as 16 bit pcm, but returns a stream of Uint8list. So I don't understand how they are representing the 16 bit pcm with 8 bit integers.

I've tried to just graph out the numbers as is, but it doesnt appear to be right. The following is the code I used to graph out 30hz sine wave, with the data sound_stream provides.

final Uint8List data; 
  @override
  void paint(Canvas canvas, Size size) { 
    double dx = size.width / data.length;
    for(int i = 1; i < data.length; i+=1){
    canvas.drawLine(Offset((i - 1) * dx, (data[i-1].toDouble()/256) * size.height), Offset((i) * dx, (data[i].toDouble()/256) * size.height),  Paint()..color = Colors.red..strokeWidth=1);
    }
  }

30hz


Solution

  • It's a Uint8List because that's a byte array and is what gets moved across the native-Dart boundary. So you need to view that byte array as a list of 16 bit integers. Use ByteBuffer to do this.

    final Uint8List data;
    final pcm16 = data.buffer.asInt16List();
    // pcm16 is an Int16List and will be half the length of data
    // expect values in pcm16 to be between -32768 and +32767 so
    // normalize by dividing by 32768.0 to get -1.0 to +1.0
    

    You will probably find that you are getting twice as many bytes as you expect. If you are sampling at 16kHz, expect 32k bytes a second, but you'll get 16000 samples a second when viewed as 16 bit ints.