|
|
@@ -1,9 +1,7 @@
|
|
1
|
1
|
import EventEmitter from '../util/EventEmitter';
|
|
2
|
2
|
import { calculateAverage } from '../util/MathUtil';
|
|
3
|
|
-
|
|
4
|
3
|
import { DETECTOR_STATE_CHANGE, VAD_TALK_WHILE_MUTED } from './DetectionEvents';
|
|
5
|
4
|
|
|
6
|
|
-
|
|
7
|
5
|
/**
|
|
8
|
6
|
* The threshold which the average VAD values for a span of time needs to exceed to trigger an event.
|
|
9
|
7
|
* @type {number}
|
|
|
@@ -28,10 +26,21 @@ const VAD_VOICE_LEVEL = 0.9;
|
|
28
|
26
|
*/
|
|
29
|
27
|
const PROCESS_TIME_FRAME_SPAN_MS = 700;
|
|
30
|
28
|
|
|
|
29
|
+export interface IVADScore {
|
|
|
30
|
+ deviceId: string;
|
|
|
31
|
+ score: number;
|
|
|
32
|
+ timestamp: Date;
|
|
|
33
|
+}
|
|
|
34
|
+
|
|
31
|
35
|
/**
|
|
32
|
36
|
* Detect if provided VAD score which is generated on a muted device is voice and fires an event.
|
|
33
|
37
|
*/
|
|
34
|
38
|
export default class VADTalkMutedDetection extends EventEmitter {
|
|
|
39
|
+ private _processing: boolean;
|
|
|
40
|
+ private _scoreArray: number[];
|
|
|
41
|
+ private _active: boolean;
|
|
|
42
|
+ private _processTimeout?: ReturnType<typeof setTimeout>;
|
|
|
43
|
+
|
|
35
|
44
|
/**
|
|
36
|
45
|
* Creates <tt>VADTalkMutedDetection</tt>
|
|
37
|
46
|
* @constructor
|
|
|
@@ -54,7 +63,6 @@ export default class VADTalkMutedDetection extends EventEmitter {
|
|
54
|
63
|
* Current mute state of the audio track being monitored.
|
|
55
|
64
|
*/
|
|
56
|
65
|
this._active = false;
|
|
57
|
|
-
|
|
58
|
66
|
this._calculateVADScore = this._calculateVADScore.bind(this);
|
|
59
|
67
|
}
|
|
60
|
68
|
|
|
|
@@ -63,8 +71,8 @@ export default class VADTalkMutedDetection extends EventEmitter {
|
|
63
|
71
|
* @returns {void}
|
|
64
|
72
|
* @fires VAD_TALK_WHILE_MUTED
|
|
65
|
73
|
*/
|
|
66
|
|
- _calculateVADScore() {
|
|
67
|
|
- const score = calculateAverage(this._scoreArray);
|
|
|
74
|
+ private _calculateVADScore(): void {
|
|
|
75
|
+ const score = calculateAverage(new Float32Array(this._scoreArray));
|
|
68
|
76
|
|
|
69
|
77
|
if (score > VAD_AVG_THRESHOLD) {
|
|
70
|
78
|
this.emit(VAD_TALK_WHILE_MUTED);
|
|
|
@@ -84,7 +92,7 @@ export default class VADTalkMutedDetection extends EventEmitter {
|
|
84
|
92
|
* @param {boolean} active
|
|
85
|
93
|
* @fires DETECTOR_STATE_CHANGE
|
|
86
|
94
|
*/
|
|
87
|
|
- _setActiveState(active) {
|
|
|
95
|
+ private _setActiveState(active: boolean): void {
|
|
88
|
96
|
this._active = active;
|
|
89
|
97
|
this.emit(DETECTOR_STATE_CHANGE, this._active);
|
|
90
|
98
|
}
|
|
|
@@ -94,7 +102,7 @@ export default class VADTalkMutedDetection extends EventEmitter {
|
|
94
|
102
|
*
|
|
95
|
103
|
* @param {boolean} isMuted - Is the device muted or not.
|
|
96
|
104
|
*/
|
|
97
|
|
- changeMuteState(isMuted) {
|
|
|
105
|
+ public changeMuteState(isMuted: boolean): void {
|
|
98
|
106
|
// This service only needs to run when the microphone is muted.
|
|
99
|
107
|
this._setActiveState(isMuted);
|
|
100
|
108
|
this.reset();
|
|
|
@@ -105,7 +113,7 @@ export default class VADTalkMutedDetection extends EventEmitter {
|
|
105
|
113
|
*
|
|
106
|
114
|
* @returns {boolean}
|
|
107
|
115
|
*/
|
|
108
|
|
- isActive() {
|
|
|
116
|
+ public isActive(): boolean {
|
|
109
|
117
|
return this._active;
|
|
110
|
118
|
}
|
|
111
|
119
|
|
|
|
@@ -118,12 +126,13 @@ export default class VADTalkMutedDetection extends EventEmitter {
|
|
118
|
126
|
* @param {string} vadScore.deviceId - Device id of the associated track.
|
|
119
|
127
|
* @listens VAD_SCORE_PUBLISHED
|
|
120
|
128
|
*/
|
|
121
|
|
- processVADScore(vadScore) {
|
|
|
129
|
+ public processVADScore(vadScore: IVADScore): void {
|
|
122
|
130
|
if (!this._active) {
|
|
123
|
131
|
return;
|
|
124
|
132
|
}
|
|
125
|
|
-
|
|
126
|
133
|
// There is a processing phase on going, add score to buffer array.
|
|
|
134
|
+
|
|
|
135
|
+
|
|
127
|
136
|
if (this._processing) {
|
|
128
|
137
|
this._scoreArray.push(vadScore.score);
|
|
129
|
138
|
|
|
|
@@ -146,7 +155,7 @@ export default class VADTalkMutedDetection extends EventEmitter {
|
|
146
|
155
|
*
|
|
147
|
156
|
* @returns {void}
|
|
148
|
157
|
*/
|
|
149
|
|
- reset() {
|
|
|
158
|
+ public reset(): void {
|
|
150
|
159
|
this._processing = false;
|
|
151
|
160
|
this._scoreArray = [];
|
|
152
|
161
|
clearTimeout(this._processTimeout);
|