c# - Recording WAV to IBM Watson Speech-To-Text -
i'm trying record audio , send ibm watson speech-to-text transcription. i've tested watson wav file loaded disk, , worked. on other end, i've tested recording microphone , storing disk, works too.
but when try record audio naudio wavein, result watson empty, if there's no audio.
anyone can shine light on this, or has ideas?
private async void starthere() { var ws = new clientwebsocket(); ws.options.credentials = new networkcredential("*****", "*****"); await ws.connectasync(new uri("wss://stream.watsonplatform.net/speech-to-text/api/v1/recognize?model=en-us_narrowbandmodel"), cancellationtoken.none); task.waitall(ws.sendasync(openingmessage, websocketmessagetype.text, true, cancellationtoken.none), handleresults(ws)); record(); } public void record() { var wavein = new waveinevent { buffermilliseconds = 50, devicenumber = 0, waveformat = format }; wavein.dataavailable += new eventhandler(wavein_dataavailable); wavein.recordingstopped += new eventhandler(wavein_recordingstopped); wavein.startrecording(); } public void stop() { await ws.sendasync(closingmessage, websocketmessagetype.text, true, cancellationtoken.none); } public void close() { ws.closeasync(websocketclosestatus.normalclosure, "close", cancellationtoken.none).wait(); } private void wavein_dataavailable(object sender, waveineventargs e) { await ws.sendasync(new arraysegment(e.buffer), websocketmessagetype.binary, true, cancellationtoken.none); } private async task handleresults(clientwebsocket ws) { var buffer = new byte[1024]; while (true) { var segment = new arraysegment(buffer); var result = await ws.receiveasync(segment, cancellationtoken.none); if (result.messagetype == websocketmessagetype.close) { return; } int count = result.count; while (!result.endofmessage) { if (count >= buffer.length) { await ws.closeasync(websocketclosestatus.invalidpayloaddata, "that's long", cancellationtoken.none); return; } segment = new arraysegment(buffer, count, buffer.length - count); result = await ws.receiveasync(segment, cancellationtoken.none); count += result.count; } var message = encoding.utf8.getstring(buffer, 0, count); // you'll want parse json useful object here, // see servicestate , isdelimeter light-weight example of that. console.writeline(message); if (isdelimeter(message)) { return; } } } private bool isdelimeter(string json) { memorystream stream = new memorystream(encoding.utf8.getbytes(json)); datacontractjsonserializer ser = new datacontractjsonserializer(typeof(servicestate)); servicestate obj = (servicestate) ser.readobject(stream); return obj.state == "listening"; } [datacontract] internal class servicestate { [datamember] public string state = ""; } edit: i've tried send wav "header" prior startrecording, this
wavein.dataavailable += new eventhandler(wavein_dataavailable); wavein.recordingstopped += new eventhandler(wavein_recordingstopped); /* send wav "header" first */ using (var stream = new memorystream()) { using (var writer = new binarywriter(stream, encoding.utf8)) { writer.write(encoding.utf8.getbytes("riff")); writer.write(0); // placeholder writer.write(encoding.utf8.getbytes("wave")); writer.write(encoding.utf8.getbytes("fmt ")); format.serialize(writer); if (format.encoding != waveformatencoding.pcm && format.bitspersample != 0) { writer.write(encoding.utf8.getbytes("fact")); writer.write(4); writer.write(0); } writer.write(encoding.utf8.getbytes("data")); writer.write(0); writer.flush(); } byte[] header = stream.toarray(); await ws.sendasync(new arraysegment(header), websocketmessagetype.binary, true, cancellationtoken.none); } /* end wav header */ wavein.startrecording();
found solution after ~20 hours of trial , error, created github gist, because may handy others. see https://gist.github.com/kboek/20476c2a03b5e9188edebaace74f9a07
Comments
Post a Comment