Skip to content

Instantly share code, notes, and snippets.

@codyromano
Created April 9, 2016 00:37
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save codyromano/91ce828d76c34c9c32f8c246bdd9edc2 to your computer and use it in GitHub Desktop.
Save codyromano/91ce828d76c34c9c32f8c246bdd9edc2 to your computer and use it in GitHub Desktop.
/**
* @module RetroRecorder
* @author Cody Romano
* @desc This is just a demo to illustrate how RetroRecorder might be implemented.
* Please take it with a grain of salt because it's not optimized and the Speech API
* probably isn't the best implementation.
*/
(function(exports) {
'use strict';
var proto = RetroRecorder.prototype;
function RetroRecorder() {
/* After you grant the recorder permission it will record a
continous stream of audio, deleting itself every x milliseconds,
where x is the duration you specify here */
this.continuousStreamDuration = 15 * 1000;
// All the text captured by the continuous stream
this.speechResults = [];
// Just the text that has been marked as important
this.savedResults = {};
this.sessionStartTime = null;
if (!'webkitSpeechRecognition' in window) {
throw new Error('Browser does not support Speech API');
}
this.speechAPI = new webkitSpeechRecognition();
// Keep recording until we tell the browser to stop
this.speechAPI.continuous = true;
// Don't report results until confidence is high
this.speechAPI.interimResults = false;
this.speechAPI.onresult = recordSpeechResult.bind(this);
}
proto.start = function() {
this.sessionStartTime = new Date().getTime();
this.speechAPI.start();
};
proto.stop = function() {
this.speechAPI.stop();
};
proto.saveRecentSpeech = function(seconds) {
var _self = this;
var recent = this.getRecentSpeech(seconds);
console.log('getRecentSpeech(' + seconds + '): ', recent);
/* Store */
recent.forEach(function(speechEntry) {
_self.savedResults[speechEntry.timeStamp] = speechEntry;
});
};
proto.getSavedSpeech = function() {
var _self = this;
var timeStamps = Object.keys(this.savedResults);
var array = [];
var result = timeStamps.reduce(function(result, timeStamp) {
result.push(_self.savedResults[timeStamp].text);
return result;
}, []);
return result.join('');
};
proto.getRecentSpeech = function(seconds) {
var lowerbound = this.getSessionDuration() - (seconds * 1000),
filterFn = filterByTimestamp.bind(null, lowerbound);
return this.speechResults.filter(filterFn);
};
proto.getSessionDuration = function() {
if (this.sessionStartTime) {
return new Date().getTime() - this.sessionStartTime;
}
};
/* This method is called whenever a new sentence is recorded.
You can override it if you want to provide some functionality here -
e.g. displaying a mic graphic to show recording is in progress. */
proto.onSpeechAdded = function() {};
function recordSpeechResult(event) {
// Convert the SpeechRecognitionList to an array
var speechResults = Array.prototype.slice.call(event.results),
mostRecentText = getTranscript(tail(speechResults));
var removeOldResults = filterByTimestamp.bind(null,
this.continuousStreamDuration * 2);
this.speechResults = this.speechResults.filter(removeOldResults);
var entry = {
text: mostRecentText + '.',
timeStamp: event.timeStamp
};
this.speechResults.push(entry);
this.onSpeechAdded(entry);
}
function getTranscript(speechResult) {
var alternative = speechResult[0];
if (alternative) {
return alternative.transcript;
}
}
function filterByTimestamp(lowerbound, speechEvent) {
return speechEvent.timeStamp >= Math.max(lowerbound, 0);
}
function tail(array) {
var i = Math.max(array.length - 1, 0);
return array[i];
}
exports.RetroRecorder = RetroRecorder;
})(window);
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment