Wednesday, 15 June 2011

c# - How to split a wav file on WP8? -



c# - How to split a wav file on WP8? -

is there way split wav file in c# wp8? i'd save sample of wav file, starting at, example, 00:30 , ending @ 00:40.

maybe using kind of stream or buffer, i'd have know when start/finish copying stream wav file.

how can this?

since wav file's header can vary 44 (standard) on 100 bytes, you'll need first determine exact size of header , read of import meta info before can start chopping wav file(s).

so need know next meta info wav file(s),

sample rate, bit depth, channel count, audio info format (whether samples pcm or floating-point) header size.

before continuing, i'd recommend reading format of wav file header first you'll have improve thought of code doing.

so first need our meta info,

private void readmetadata(filestream stream, out bool isfloatinfpoint, out int channelcount, out int samplerate, out int bitdepth, out int headersize) { var headerbytes = new byte[200]; // read header bytes. stream.position = 0; stream.read(headerbytes, 0, 200); headersize = new string(encoding.ascii.getchars(headerbytes)).indexof("data") + 8; isfloatinfpoint = bitconverter.touint16(new byte[] { headerbytes[20], headerbytes[21] }, 0) == 3 ? true : false; channelcount = bitconverter.touint16(new byte[] { headerbytes[22] , headerbytes[23] }, 0); samplerate = (int)bitconverter.touint32(new byte[] { headerbytes[24], headerbytes[25], headerbytes[26], headerbytes[27] }, 0); bitdepth = bitconverter.touint16(new byte[] { headerbytes[34], headerbytes[35] }, 0); }

once have info can calculate need start , stop reading our file. calculate start , end indexes do,

var startindex = (int)(start.totalseconds * samplerate * bytedepth * channelcount); var endindex = (int)(end.totalseconds * samplerate * bytedepth * channelcount);

start & end timespan indicating when start , stop cropping.

we can read bytes our file using our newly calculated info, if you're using filestream following,

var newbytes = new byte[endindex - startindex]; mystream.position = headersize + startindex; // add together headersize position create sure don't read header. mystream.read(newbytes, 0, newbytes.length);

the have write wav header destination file along newly extracted audio. so, putting altogether should end this,

private void cropwavfile(string inputfilepath, string outputfilepath, timespan start, timespan end) { var stream = new filestream(inputfilepath, filemode.open); var newstream = new filestream(outputfilepath, filemode.openorcreate); var isfloatingpoint = false; var samplerate = 0; var bitdepth = 0; var channelcount = 0; var headersize = 0; // meta info readmetadata(stream, out isfloatingpoint, out channelcount, out samplerate, out bitdepth, out headersize); // calculate need start , stop reading. var startindex = (int)(start.totalseconds * samplerate * (bitdepth / 8) * channelcount); var endindex = (int)(end.totalseconds * samplerate * (bitdepth / 8) * channelcount); var bytescount = endindex - startindex; var newbytes = new byte[bytescount]; // read sound data. stream.position = startindex + headersize; stream.read(newbytes, 0, bytescount); // write wav header , our newly extracted sound new wav file. writemetadata(newstream, isfloatingpoint, (ushort)channelcount, (ushort)bitdepth, samplerate, newbytes.length / (bitdepth / 8)); newstream.write(newbytes, 0, newbytes.length); stream.dispose(); newstream.dispose(); } private void writemetadata(filestream stream, bool isfloatingpoint, ushort channels, ushort bitdepth, int samplerate, int totalsamplecount) { stream.position = 0; // riff header. // chunk id. stream.write(encoding.ascii.getbytes("riff"), 0, 4); // chunk size. stream.write(bitconverter.getbytes(((bitdepth / 8) * totalsamplecount) + 36), 0, 4); // format. stream.write(encoding.ascii.getbytes("wave"), 0, 4); // sub-chunk 1. // sub-chunk 1 id. stream.write(encoding.ascii.getbytes("fmt "), 0, 4); // sub-chunk 1 size. stream.write(bitconverter.getbytes(16), 0, 4); // sound format (floating point (3) or pcm (1)). other format indicates compression. stream.write(bitconverter.getbytes((ushort)(isfloatingpoint ? 3 : 1)), 0, 2); // channels. stream.write(bitconverter.getbytes(channels), 0, 2); // sample rate. stream.write(bitconverter.getbytes(samplerate), 0, 4); // bytes rate. stream.write(bitconverter.getbytes(samplerate * channels * (bitdepth / 8)), 0, 4); // block align. stream.write(bitconverter.getbytes((ushort)channels * (bitdepth / 8)), 0, 2); // bits per sample. stream.write(bitconverter.getbytes(bitdepth), 0, 2); // sub-chunk 2. // sub-chunk 2 id. stream.write(encoding.ascii.getbytes("data"), 0, 4); // sub-chunk 2 size. stream.write(bitconverter.getbytes((bitdepth / 8) * totalsamplecount), 0, 4); } private void readmetadata(filestream stream, out bool isfloatinfpoint, out int channelcount, out int samplerate, out int bitdepth, out int headersize) { var headerbytes = new byte[200]; // read header bytes. stream.position = 0; stream.read(headerbytes, 0, 200); headersize = new string(encoding.ascii.getchars(headerbytes)).indexof("data") + 8; isfloatinfpoint = bitconverter.touint16(new byte[] { headerbytes[20], headerbytes[21] }, 0) == 3 ? true : false; channelcount = bitconverter.touint16(new byte[] { headerbytes[22] , headerbytes[23] }, 0); samplerate = (int)bitconverter.touint32(new byte[] { headerbytes[24], headerbytes[25], headerbytes[26], headerbytes[27] }, 0); bitdepth = bitconverter.touint16(new byte[] { headerbytes[34], headerbytes[35] }, 0); }

c# windows-phone-8 split wav

No comments:

Post a Comment