Skip to content

Commit ae8d444

Browse files
committed
added push-to-talk mode to voice recorder demo
1 parent 7303ce6 commit ae8d444

File tree

1 file changed

+60
-39
lines changed

1 file changed

+60
-39
lines changed

voice-recorder-demo.html

Lines changed: 60 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@ <h2>Recorder</h2>
3737
<div class="group"><label>Mode:</label><select id="micModeSelect" onchange="setMicMode(this.value);">
3838
<option value="toggle" selected>Toggle ON/OFF</option>
3939
<option value="toggle-vad">Toggle ON/VAD OFF</option>
40-
<!--<option value="push-to-talk">Push-to-talk</option> TODO -->
40+
<option value="push-to-talk">Push-to-talk</option>
4141
</select></div>
4242
<div class="group"><label>Start/Stop:</label><button id="micButton"></button></div>
4343
<div class="group"><label>Gain:</label><input id="microphoneGain" class="small" type="number" value="1.0" min="0.1" max="100" step="0.1"></div>
@@ -77,6 +77,7 @@ <h2>Log <button class="variant-2" onclick="clearMessages()" style="margin: 0 0 0
7777
var micMode = document.getElementById("micModeSelect").value; //"toggle", "toggle-vad" - TODO: "push-to-talk"
7878
var isLoading = false;
7979
var isRecording = false;
80+
var hasBeenAborted = false; //used when stop came too fast (before 'ready')
8081
var wavEncoderIsBuffering = false;
8182
var sourceInfo = "-?-";
8283
var sourceInfoEle = document.getElementById("recoderInfo");
@@ -96,41 +97,47 @@ <h2>Log <button class="variant-2" onclick="clearMessages()" style="margin: 0 0 0
9697
}
9798

9899
function toggleMic(){
99-
if (!isLoading && !isRecording){
100-
isLoading = true;
101-
resetSamplesBuffer();
102-
setMicState("loading");
103-
//for this demo we create a new recorder each time
104-
SepiaVoiceRecorder.stopAndReleaseIfActive(function(){
105-
SepiaFW.webAudio.tryNativeStreamResampling = false; //try native resampling?
106-
//build options
107-
SepiaVoiceRecorder.create({
108-
//fileUrl: "test-sounds/chatter_counting.ogg", //alternative source?
109-
targetSampleRate: 16000, //this is the default for voice recorder
110-
resampleQuality: 4, //1 [fastest] - 10 [best quality]
111-
gain: +gainNode.value,
112-
recordingLimitMs: 30000, //Total recording limit ms (use to limit WAV size for example)
113-
vad: {mode: 3, maxSequenceTime: 5000}, //Switch VAD module on/off - Boolean or options object
114-
//asr: false //Switch ASR module on/off - Boolean or options object - ASR OFF = WAV encoder
115-
});
100+
if (hasBeenAborted){
101+
//wait
102+
}else if (!isLoading && !isRecording){
103+
startMic();
104+
}else{
105+
stopMic();
106+
}
107+
}
108+
function startMic(){
109+
isLoading = true;
110+
resetSamplesBuffer();
111+
setMicState("loading");
112+
//for this demo we create a new recorder each time
113+
SepiaVoiceRecorder.stopAndReleaseIfActive(function(){
114+
SepiaFW.webAudio.tryNativeStreamResampling = false; //try native resampling?
115+
//build options
116+
SepiaVoiceRecorder.create({
117+
//fileUrl: "test-sounds/chatter_counting.ogg", //alternative source?
118+
targetSampleRate: 16000, //this is the default for voice recorder
119+
resampleQuality: 4, //1 [fastest] - 10 [best quality]
120+
gain: +gainNode.value,
121+
recordingLimitMs: 30000, //Total recording limit ms (use to limit WAV size for example)
122+
vad: {mode: 3, maxSequenceTime: 5000}, //Switch VAD module on/off - Boolean or options object
123+
//asr: false //Switch ASR module on/off - Boolean or options object - ASR OFF = WAV encoder
116124
});
117-
118-
}else if (isRecording){
125+
});
126+
}
127+
function stopMic(){
128+
if (isRecording){
119129
SepiaVoiceRecorder.stop();
120-
121130
}else if (isLoading){
131+
hasBeenAborted = true;
122132
setMicState("loading");
123-
SepiaVoiceRecorder.stopAndReleaseIfActive(function(){
124-
isLoading = false;
125-
isRecording = false;
126-
setMicState("idle");
127-
});
128133
}
129134
}
130135
function releaseMic(callback){
136+
setMicState("loading");
131137
SepiaVoiceRecorder.stopAndReleaseIfActive(function(){
132138
isLoading = false;
133139
isRecording = false;
140+
hasBeenAborted = false;
134141
samplesReceived = null;
135142
addMessage("RELEASED Microphone");
136143
setMicState("idle");
@@ -141,6 +148,7 @@ <h2>Log <button class="variant-2" onclick="clearMessages()" style="margin: 0 0 0
141148
setMicState("error");
142149
isRecording = false;
143150
isLoading = false;
151+
hasBeenAborted = false;
144152
}
145153

146154
SepiaVoiceRecorder.onProcessorReady = function(info){
@@ -152,7 +160,11 @@ <h2>Log <button class="variant-2" onclick="clearMessages()" style="margin: 0 0 0
152160
setMicState("idle");
153161
isLoading = false;
154162
isRecording = false;
155-
SepiaVoiceRecorder.start();
163+
if (hasBeenAborted){
164+
releaseMic();
165+
}else{
166+
SepiaVoiceRecorder.start();
167+
}
156168
}
157169
SepiaVoiceRecorder.onProcessorInitError = function(err){
158170
console.error("SepiaVoiceRecorder - onProcessorInitError", err);
@@ -189,8 +201,7 @@ <h2>Log <button class="variant-2" onclick="clearMessages()" style="margin: 0 0 0
189201
SepiaVoiceRecorder.onProcessorRelease = function(info){
190202
console.log("SepiaVoiceRecorder - onProcessorRelease");
191203
setMicState("idle");
192-
isRecording = false;
193-
isLoading = false;
204+
hasBeenAborted = false;
194205
}
195206

196207
SepiaVoiceRecorder.onDebugLog = function(msg){}
@@ -201,7 +212,7 @@ <h2>Log <button class="variant-2" onclick="clearMessages()" style="margin: 0 0 0
201212
if (data.rms != undefined){
202213
setVolume(data.rms);
203214
}
204-
if (showAudioSamplesCheckbox.checked && data.samples){
215+
if (showAudioSamplesCheckbox.checked && data.samples && samplesReceived){
205216
//plot the wave-form now and then
206217
samplesReceived.push(data.samples);
207218
if (samplesReceived.framesAvailable >= plotSamplesN){
@@ -298,19 +309,29 @@ <h2>Log <button class="variant-2" onclick="clearMessages()" style="margin: 0 0 0
298309
var micLongPressTimer = undefined;
299310
var micIsLongPress = false;
300311
micButton.addEventListener('pointerdown', function(event){
301-
clearTimeout(micLongPressTimer);
302-
micLongPressTimer = setTimeout(function(){
303-
onMicLongPress();
304-
}, 1000);
312+
if (micMode == "push-to-talk"){
313+
if (!isLoading && !isRecording && !hasBeenAborted){
314+
startMic();
315+
}
316+
}else{
317+
clearTimeout(micLongPressTimer);
318+
micLongPressTimer = setTimeout(function(){
319+
onMicLongPress();
320+
}, 1000);
321+
}
305322
});
306323
micButton.addEventListener('pointerup', function(event){
307-
clearTimeout(micLongPressTimer);
308-
if (!micIsLongPress){
309-
toggleMic();
324+
if (micMode == "push-to-talk"){
325+
stopMic();
310326
}else{
311-
setMicState("");
327+
clearTimeout(micLongPressTimer);
328+
if (!micIsLongPress){
329+
toggleMic();
330+
}else{
331+
setMicState("");
332+
}
333+
micIsLongPress = false;
312334
}
313-
micIsLongPress = false;
314335
});
315336
function onMicLongPress(){
316337
micIsLongPress = true;

0 commit comments

Comments
 (0)