c# - Convert float[] to byte[] for NAudio -
i receiving string representing array of audio samples browser captured via getusermedia. getusermedia recording @ 48000, , interleaving 2 channels before send string values server. turn string float[] so:
string[] raw = buffer.tostring().split(new char[]{ ',' }); float[] farray = new float[raw.length]; (int x = 0; x < raw.length; x++) { float sampleval = float.parse(raw[x]); farray[x] = sampleval; } what convert float[] array byte[] array can pass bufferedwaveprovider (48000, 16, 1) playback. here's how trying conversion:
byte[] bsamples = new byte[farray.length * 2]; (int x = 0; x < farray.length; x += 2) { short ssample = (short)math.floor(farray[x] * 32767); byte[] tmp = bitconverter.getbytes(ssample); bsamples[x] = tmp[0]; bsamples[x + 1] = tmp[1]; } using code above, garbage produced. can point me in right direction doing such conversion?
i've seen this, didn't me need go.
it looks indexing isn't quite right in second loop. you're looping on float samples, , using same index in short output:
for (int x = 0; x < farray.length; x += 2) another thing (let's assume floating-point input true ieee 32-bit float samples in range [-1.0,1.0], won't worry converting). stereo input? if so, you'll need combine samples before converting 'short'. that's easy do. average successive pairs of float values (left channel/right channel).
the size of output array should correct. technically, it'd this:
int inchannels = 2; // doesn't have variable, shows 'stereo' input. int numsamples = farray.length / inchannels; byte [] bsamples = new byte [numsamples * sizeof(int16)]; then should able conversion follows. note assumes stereo input, averages float samples.
int outindex = 0; for( int inindex = 0; inindex < farray.length; inindex += 2 ) { // 'insample' average of left , right channels. isn't // entirely accurate - if 1 channel 0.0, should use // other channel verbatim. close enough. float insample = (farray[inindex] + farray[inindex+1]) / 2.0f; // output sample. it's better use int16.maxvalue // hard-coded value. int16 outsample = (int16)(insample * (float)int16.maxvalue); // i'm old-school, i'm fan of 'unsafe'. can use // bitconverter using. actually, would've // done entire conversion in 'unsafe' mode. unsafe { fixed( byte * pbyte = &bsamples[outindex] ) { int16 * p = (int16 *)pbyte; *p = outsample; outindex += sizeof(int16); } } }
Comments
Post a Comment