v0 Code to stream audio from Client to Server written
This commit is contained in:
parent
ed506d631a
commit
9f6adb3a29
|
@ -59,3 +59,5 @@ typings/
|
|||
|
||||
# next.js build output
|
||||
.next
|
||||
|
||||
dist/main.js
|
||||
|
|
|
@ -0,0 +1,13 @@
|
|||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="X-UA-Compatible" content="ie=edge">
|
||||
<title>Document</title>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<script src="main.js"></script>
|
||||
</body>
|
||||
</html>
|
|
@ -0,0 +1,20 @@
|
|||
{
|
||||
"name": "websocket-client",
|
||||
"version": "1.0.0",
|
||||
"description": "",
|
||||
"scripts": {
|
||||
"test": "echo \"Error: no test specified\" && exit 1",
|
||||
"build": "webpack",
|
||||
"start": "webpack-dev-server --open"
|
||||
},
|
||||
"author": "",
|
||||
"license": "ISC",
|
||||
"devDependencies": {
|
||||
"webpack": "^4.17.1",
|
||||
"webpack-cli": "^3.1.0",
|
||||
"webpack-dev-server": "^3.1.7"
|
||||
},
|
||||
"dependencies": {
|
||||
"socket.io-client": "^2.1.1"
|
||||
}
|
||||
}
|
|
@ -0,0 +1,84 @@
|
|||
import io from 'socket.io-client';
|
||||
|
||||
/**
|
||||
* The Class Responsible for Talking with Polyglot-Node
|
||||
* @param {string} url - URL of NodeJS Server.
|
||||
*/
|
||||
class WebSocket {
|
||||
constructor(url) {
|
||||
this.io = io(url);
|
||||
|
||||
this.listen(() => {
|
||||
this.grabAudio();
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Create socket.io event listeners.
|
||||
* @param {Function} cb - Called once connected to server.
|
||||
*/
|
||||
listen(cb) {
|
||||
this.io.on('disconnect', (err) => {
|
||||
console.error("Disconnected from Server.");
|
||||
})
|
||||
|
||||
this.io.on('connect', (data) => {
|
||||
this.io.emit("join", "Hi There NodeJS!");
|
||||
console.log("Connected to NodeJS Server");
|
||||
cb();
|
||||
});
|
||||
}
|
||||
/**
|
||||
* This Class Grabs the Audio from the User.
|
||||
* Line 26 needs to be replaced with the global variable for localstream found in Rails TODO: Put line
|
||||
*
|
||||
* DEPRECAION WARNING. This method makes vital use of createScriptProcessor which will be scrapped at some point
|
||||
* in the future. TODO: Switch from createScriptProcessor to AudioWorklet (No documentation as of 2018-08-30)
|
||||
* @deprecated
|
||||
* @async
|
||||
*/
|
||||
async grabAudio() {
|
||||
this.io.emit('startRecognition', "en-US");
|
||||
|
||||
AudioContext = window.AudioContext || window.webkitAudioContext;
|
||||
const ctx = new AudioContext();
|
||||
const processor = ctx.createScriptProcessor(2048, 1, 1);
|
||||
processor.connect(ctx.destination);
|
||||
processor.onaudioprocess = e => this.handleBuffer(e);
|
||||
|
||||
const stream = await navigator.mediaDevices.getUserMedia({ audio: true, video: false });
|
||||
ctx.createMediaStreamSource(stream).connect(processor);
|
||||
ctx.resume();
|
||||
}
|
||||
|
||||
/**
|
||||
* Takes the Float32Array Array from the ScriptProcessor Event
|
||||
* and converts it to Int16 for Google Speech to Text use.
|
||||
* @param {AudioProcessingEvent} e Chunk of Audio w/ Audio F32Array
|
||||
*/
|
||||
handleBuffer(e) {
|
||||
let l = e.inputBuffer.getChannelData(0);
|
||||
this.io.emit('binary', convertF32ToI16(l));
|
||||
|
||||
/**
|
||||
* 32Khz to 16Khz Audio
|
||||
* Converts Float32 Buffer to Int16Buffer
|
||||
* @param {Float32Array} buffer - Float32 Buffer;
|
||||
* @returns {ArrayBuffer}
|
||||
*/
|
||||
function convertF32ToI16(buffer) {
|
||||
let l = buffer.length;
|
||||
|
||||
let buf = new Int16Array(l/3);
|
||||
|
||||
while (l--) {
|
||||
if (l % 3 == 0) {
|
||||
buf[l / 3] = buffer[l] * 0xFFFF;
|
||||
}
|
||||
}
|
||||
return buf.buffer;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const ws = new WebSocket("http://localhost:1337");
|
|
@ -0,0 +1,15 @@
|
|||
const path = require("path");
|
||||
|
||||
module.exports = {
|
||||
mode: "development",
|
||||
entry: "./src/index.js",
|
||||
devtool: 'inline-source-map',
|
||||
devServer: {
|
||||
contentBase: "./dist",
|
||||
port: 8080
|
||||
},
|
||||
output: {
|
||||
filename: "main.js",
|
||||
path: path.resolve(__dirname, "dist")
|
||||
}
|
||||
}
|
Reference in New Issue