using System;
using System.IO;
using System.Text;
using OpenTK.Audio.OpenAL;
public class WavFile
{
public byte[] Data;
public ALFormat Format; // Al.FORMAT_*
public int SampleRate;
public static WavFile Load(string path)
{
using (var fs = File.OpenRead(path))
using (var br = new BinaryReader(fs))
{
if (new string(br.ReadChars(4)) != "RIFF") throw new Exception("Not RIFF: " + path);
br.ReadInt32();
if (new string(br.ReadChars(4)) != "WAVE") throw new Exception("Not WAVE: " + path);
short channels = 0, bits = 0;
int rate = 0;
byte[] data = null;
while (fs.Position < fs.Length - 8)
{
string id = new string(br.ReadChars(4));
int len = br.ReadInt32();
if (id == "fmt ")
{
br.ReadInt16(); // audio format (1 = PCM)
channels = br.ReadInt16();
rate = br.ReadInt32();
br.ReadInt32(); // byte rate
br.ReadInt16(); // block align
bits = br.ReadInt16();
if (len > 16) br.ReadBytes(len - 16);
}
else if (id == "data")
{
data = br.ReadBytes(len);
}
else
{
br.ReadBytes(len); // skip unknown chunk
}
if ((len & 1) == 1) br.ReadByte(); // chunks are word-aligned
}
if (data == null) throw new Exception("No data chunk: " + path);
ALFormat fmt;
if (channels == 1 && bits == 8) fmt = ALFormat.Mono8;
else if (channels == 1 && bits == 16) fmt = ALFormat.Mono16;
else if (channels == 2 && bits == 8) fmt = ALFormat.Stereo8;
else if (channels == 2 && bits == 16) fmt = ALFormat.Stereo16;
else throw new Exception("Unsupported WAV: " + channels + "ch " + bits + "bit");
return new WavFile { Data = data, Format = fmt, SampleRate = rate };
}
}
}