///FIXME perhaps support extensible wav format FXbool WavOutput::configure(const AudioFormat & fmt) { FXushort format; // Can't handle big endian yet, neither does the output thread handle byteorder swaps if (fmt.byteorder() != Format::Little) return false; // Extensible Wav Format not yet supported if (fmt.channels>2) return false; // Determine format switch(fmt.datatype()) { case Format::Unsigned : case Format::Signed : format = WAV_FORMAT_PCM; break; case Format::Float : format = WAV_FORMAT_FLOAT; break; default : return false; break; } FXString path=FXPath::unique("gap.wav"); if (file.open(path,FXIO::Writing)) { GM_DEBUG_PRINT("[wav] opened output file: %s\n",path.text()); af=fmt; FXuint chunksize=0; FXlong ldata=0; /// riff chunk file.writeBlock("RIFF",4); file.writeBlock(&chunksize,4); // empty for now file.writeBlock("WAVE",4); /// junk chunk chunksize=28; file.writeBlock("JUNK",4); file.writeBlock(&chunksize,4); file.writeBlock(&ldata,8); file.writeBlock(&ldata,8); file.writeBlock(&ldata,8); chunksize=0; file.writeBlock(&chunksize,4); /// fmt file.writeBlock("fmt ",4); chunksize=16; file.writeBlock(&chunksize,4); file.writeBlock(&format,2); FXushort channels=fmt.channels; FXuint rate=fmt.rate; FXuint byterate=fmt.rate*fmt.channels*fmt.packing(); FXushort blockalign=fmt.framesize(); FXushort bitspersample=fmt.bps(); file.writeBlock(&channels,2); file.writeBlock(&rate,4); file.writeBlock(&byterate,4); file.writeBlock(&blockalign,2); file.writeBlock(&bitspersample,2); file.writeBlock("data",4); chunksize=0xFFFFFFFF; data_pos=file.position(); file.writeBlock(&chunksize,4); return true; } GM_DEBUG_PRINT("[wav] failed to open output file: %s\n",path.text()); return false; }