speaker-calibration 2.2.196 → 2.2.198
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/example/i18n.js +2334 -1957
- package/dist/main.js +15 -4
- package/package.json +1 -1
- package/src/powerCheck.js +99 -0
- package/src/server/PythonServerAPI.js +34 -0
- package/src/tasks/audioCalibrator.js +1 -2
- package/src/tasks/combination/combination.js +55 -43
package/package.json
CHANGED
|
@@ -0,0 +1,99 @@
|
|
|
1
|
+
export const volumePowerCheck = (rec, fs, preSec, Sec, _calibrateSoundPowerBinDesiredSec) => {
|
|
2
|
+
const coarseHz = 1 / _calibrateSoundPowerBinDesiredSec;
|
|
3
|
+
const power = rec.map(x => Math.pow(x, 2)); // Squared values of the signal
|
|
4
|
+
|
|
5
|
+
// Adjust coarseHz so that fs is an integer multiple of coarseHz.
|
|
6
|
+
let n = Math.round(fs / coarseHz);
|
|
7
|
+
|
|
8
|
+
// Sampling times for plotting
|
|
9
|
+
const t = Array.from({ length: power.length }, (_, i) => i / fs);
|
|
10
|
+
|
|
11
|
+
const coarseSamples = Math.ceil(power.length / n);
|
|
12
|
+
const coarsePowerDb = new Array(coarseSamples).fill(0);
|
|
13
|
+
const coarseT = new Array(coarseSamples).fill(0);
|
|
14
|
+
|
|
15
|
+
for (let i = 0; i < coarseSamples; i++) {
|
|
16
|
+
const indices = Array.from({ length: Math.min(n, power.length - i * n) }, (_, idx) => i * n + idx);
|
|
17
|
+
const extremeIndices = [indices[0], indices[indices.length - 1]];
|
|
18
|
+
|
|
19
|
+
const avgPower = indices.reduce((sum, idx) => sum + power[idx], 0) / indices.length;
|
|
20
|
+
coarsePowerDb[i] = 10 * Math.log10(avgPower);
|
|
21
|
+
|
|
22
|
+
const avgTime = (t[extremeIndices[0]] + t[extremeIndices[1]]) / 2;
|
|
23
|
+
coarseT[i] = avgTime;
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
const prepSamples = Math.round(coarseHz * preSec);
|
|
27
|
+
const postSamples = Math.round(coarseHz * (preSec + Sec));
|
|
28
|
+
const sd = Math.round(standardDeviation(coarsePowerDb.slice(prepSamples)) * 10) / 10;
|
|
29
|
+
|
|
30
|
+
const coarseTRounded = coarseT.map(t => Math.round(t * 1000) / 1000); // Round to 3 decimal places
|
|
31
|
+
const coarsePowerDbRounded = coarsePowerDb.map(db => Math.round(db * 1000) / 1000); // Round to 3 decimal places
|
|
32
|
+
|
|
33
|
+
const start = interpolate(coarseT, coarsePowerDb, preSec);
|
|
34
|
+
const end = interpolate(coarseT, coarsePowerDb, preSec + Sec);
|
|
35
|
+
|
|
36
|
+
let preT = coarseTRounded.slice(0, prepSamples);
|
|
37
|
+
let preDb = coarsePowerDbRounded.slice(0, prepSamples);
|
|
38
|
+
|
|
39
|
+
// Adjust starting point of preT and preDb
|
|
40
|
+
if (preT[preT.length - 1] < preSec) {
|
|
41
|
+
preT.push(preSec);
|
|
42
|
+
preDb.push(start);
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
let recT = coarseTRounded.slice(prepSamples, postSamples);
|
|
46
|
+
let recDb = coarsePowerDbRounded.slice(prepSamples, postSamples);
|
|
47
|
+
|
|
48
|
+
if (recT[0] > preSec) {
|
|
49
|
+
recT.unshift(preSec);
|
|
50
|
+
recDb.unshift(start);
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
if (recT[recT.length - 1] < preSec + Sec) {
|
|
54
|
+
recT.push(preSec + Sec);
|
|
55
|
+
recDb.push(end);
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
let postT = coarseTRounded.slice(postSamples);
|
|
59
|
+
let postDb = coarsePowerDbRounded.slice(postSamples);
|
|
60
|
+
|
|
61
|
+
if (postT[0] > preSec + Sec) {
|
|
62
|
+
postT.unshift(preSec + Sec);
|
|
63
|
+
postDb.unshift(end);
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
return { preT, preDb, recT, recDb, postT, postDb, sd };
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
// Helper function for interpolation
|
|
70
|
+
export const interpolate = (x, y, target) => {
|
|
71
|
+
let lowIdx = 0;
|
|
72
|
+
while (lowIdx < x.length - 1 && x[lowIdx] < target) {
|
|
73
|
+
lowIdx++;
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
const x0 = x[lowIdx - 1];
|
|
77
|
+
const y0 = y[lowIdx - 1];
|
|
78
|
+
const x1 = x[lowIdx];
|
|
79
|
+
const y1 = y[lowIdx];
|
|
80
|
+
|
|
81
|
+
// Linear interpolation
|
|
82
|
+
return y0 + ((target - x0) * (y1 - y0)) / (x1 - x0);
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
// Helper function to calculate standard deviation
|
|
86
|
+
export const standardDeviation = (arr) => {
|
|
87
|
+
const mean = arr.reduce((sum, val) => sum + val, 0) / arr.length;
|
|
88
|
+
const variance = arr.reduce((sum, val) => sum + Math.pow(val - mean, 2), 0) / arr.length;
|
|
89
|
+
return Math.sqrt(variance);
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
export const getPower = (dataArray) => {
|
|
93
|
+
const squaredValues = dataArray.map(value => value * value);
|
|
94
|
+
const sum_of_squares = squaredValues.reduce((total, value) => total + value, 0);
|
|
95
|
+
const squared_mean = sum_of_squares / dataArray.length;
|
|
96
|
+
const dbLevel = 20 * Math.log10(Math.sqrt(squared_mean));
|
|
97
|
+
const roundedDbLevel = Math.round(dbLevel * 10) / 10;
|
|
98
|
+
return roundedDbLevel;
|
|
99
|
+
}
|
|
@@ -830,6 +830,40 @@ class PythonServerAPI {
|
|
|
830
830
|
});
|
|
831
831
|
return res.data[task];
|
|
832
832
|
};
|
|
833
|
+
|
|
834
|
+
volumePowerCheckWithRetry = async ({
|
|
835
|
+
payload,
|
|
836
|
+
sampleRate,
|
|
837
|
+
preSec,
|
|
838
|
+
Sec,
|
|
839
|
+
binDesiredSec
|
|
840
|
+
}) => {
|
|
841
|
+
let retryCount = 0;
|
|
842
|
+
let response = null;
|
|
843
|
+
|
|
844
|
+
while (retryCount < this.MAX_RETRY_COUNT) {
|
|
845
|
+
try {
|
|
846
|
+
response = await this.volumePowerCheck({
|
|
847
|
+
payload,
|
|
848
|
+
sampleRate,
|
|
849
|
+
preSec,
|
|
850
|
+
Sec,
|
|
851
|
+
binDesiredSec});
|
|
852
|
+
// If the request is successful, break out of the loop
|
|
853
|
+
break;
|
|
854
|
+
} catch (error) {
|
|
855
|
+
console.error(`Error occurred. Retrying... (${retryCount + 1}/${this.MAX_RETRY_COUNT})`);
|
|
856
|
+
retryCount++;
|
|
857
|
+
await new Promise(resolve => setTimeout(resolve, this.RETRY_DELAY_MS));
|
|
858
|
+
}
|
|
859
|
+
}
|
|
860
|
+
|
|
861
|
+
if (response) {
|
|
862
|
+
return response;
|
|
863
|
+
} else {
|
|
864
|
+
throw new Error(`Failed to get volume power check after ${this.MAX_RETRY_COUNT} attempts.`);
|
|
865
|
+
}
|
|
866
|
+
};
|
|
833
867
|
}
|
|
834
868
|
|
|
835
869
|
export default PythonServerAPI;
|
|
@@ -82,7 +82,6 @@ class AudioCalibrator extends AudioRecorder {
|
|
|
82
82
|
mode,
|
|
83
83
|
checkRec
|
|
84
84
|
) => {
|
|
85
|
-
this.numSuccesfulCaptures = 0;
|
|
86
85
|
console.warn('before recording background noise');
|
|
87
86
|
// calibration loop
|
|
88
87
|
while (loopCondition()) {
|
|
@@ -213,7 +212,7 @@ class AudioCalibrator extends AudioRecorder {
|
|
|
213
212
|
if (this.isCalibrating) break;
|
|
214
213
|
// after recording
|
|
215
214
|
await afterRecord(lCalib);
|
|
216
|
-
const sd = await checkSD();
|
|
215
|
+
const sd = await checkSD() || Infinity;
|
|
217
216
|
if (sd <= maxSD) {
|
|
218
217
|
console.log(`SD =${sd}, less than calibrateSound1000HzMaxSD_dB=${maxSD}`);
|
|
219
218
|
this.numCalibratingRoundsCompleted += 2;
|
|
@@ -11,6 +11,12 @@ import {
|
|
|
11
11
|
standardDeviation,
|
|
12
12
|
interpolate,
|
|
13
13
|
} from '../../utils';
|
|
14
|
+
|
|
15
|
+
import {
|
|
16
|
+
volumePowerCheck,
|
|
17
|
+
getPower
|
|
18
|
+
} from '../../powerCheck';
|
|
19
|
+
|
|
14
20
|
import database from '../../config/firebase';
|
|
15
21
|
import {ref, set, get, child} from 'firebase/database';
|
|
16
22
|
import {
|
|
@@ -353,7 +359,7 @@ class Combination extends AudioCalibrator {
|
|
|
353
359
|
* @example
|
|
354
360
|
*/
|
|
355
361
|
sendSystemImpulseResponsesToServerForProcessing = async () => {
|
|
356
|
-
this.addTimeStamp('Get system
|
|
362
|
+
this.addTimeStamp('Get system IIR');
|
|
357
363
|
const computedIRs = await Promise.all(this.impulseResponses);
|
|
358
364
|
const filteredComputedIRs = computedIRs.filter(element => {
|
|
359
365
|
return element != undefined;
|
|
@@ -430,7 +436,7 @@ class Combination extends AudioCalibrator {
|
|
|
430
436
|
* @example
|
|
431
437
|
*/
|
|
432
438
|
sendComponentImpulseResponsesToServerForProcessing = async () => {
|
|
433
|
-
this.addTimeStamp('Get component
|
|
439
|
+
this.addTimeStamp('Get component IIR');
|
|
434
440
|
const computedIRs = await Promise.all(this.impulseResponses);
|
|
435
441
|
const filteredComputedIRs = computedIRs.filter(element => {
|
|
436
442
|
return element != undefined;
|
|
@@ -538,7 +544,7 @@ class Combination extends AudioCalibrator {
|
|
|
538
544
|
// Slice the array from the calculated start index to the end of the array
|
|
539
545
|
const background_rec = background_rec_whole.slice(startIndex);
|
|
540
546
|
console.log('Sending background recording to server for processing');
|
|
541
|
-
this.addTimeStamp('
|
|
547
|
+
this.addTimeStamp('Compute background PSD');
|
|
542
548
|
this.pyServerAPI
|
|
543
549
|
.getBackgroundNoisePSDWithRetry({
|
|
544
550
|
background_rec,
|
|
@@ -601,7 +607,7 @@ class Combination extends AudioCalibrator {
|
|
|
601
607
|
this.clearLastUnfilteredRecordedSignals();
|
|
602
608
|
this.numSuccessfulCaptured +=1;
|
|
603
609
|
} else {
|
|
604
|
-
if (result['sd']
|
|
610
|
+
if (result['sd'] <= this._calibrateSoundBurstMaxSD_dB) {
|
|
605
611
|
console.log('SD: ' + result['sd'] + ', less than _calibrateSoundBurstMaxSD_dB: ' + this._calibrateSoundBurstMaxSD_dB);
|
|
606
612
|
} else {
|
|
607
613
|
console.log('SD: ' + result['sd'] + ', greater than _calibrateSoundBurstMaxSD_dB: ' + this._calibrateSoundBurstMaxSD_dB);
|
|
@@ -618,7 +624,6 @@ class Combination extends AudioCalibrator {
|
|
|
618
624
|
this.recordingChecks['unfiltered'].pop();
|
|
619
625
|
}
|
|
620
626
|
this.recordingChecks['unfiltered'].push(result);
|
|
621
|
-
await this.pyServerAPI.checkMemory();
|
|
622
627
|
// let start = new Date().getTime() / 1000;
|
|
623
628
|
// const payloadT = tf.tensor1d(payload);
|
|
624
629
|
// payloadT.print();
|
|
@@ -631,6 +636,7 @@ class Combination extends AudioCalibrator {
|
|
|
631
636
|
// console.log("dimention:", xfft.shape);
|
|
632
637
|
// let end = new Date().getTime() / 1000;
|
|
633
638
|
// console.log("Time taken:", end - start, "seconds");
|
|
639
|
+
console.log('start calculate impulse response');
|
|
634
640
|
const usedPeriodStart = this.num_mls_to_skip * this.sourceSamplingRate;
|
|
635
641
|
const payload_skipped_warmUp = payload.slice(usedPeriodStart);
|
|
636
642
|
await this.pyServerAPI
|
|
@@ -645,7 +651,6 @@ class Combination extends AudioCalibrator {
|
|
|
645
651
|
this.fs2 = res['fs2'];
|
|
646
652
|
this.L_new_n = res['L_new_n'];
|
|
647
653
|
this.dL_n = res['dL_n'];
|
|
648
|
-
await this.pyServerAPI.checkMemory();
|
|
649
654
|
this.impulseResponses.push(
|
|
650
655
|
await this.pyServerAPI
|
|
651
656
|
.getImpulseResponse({
|
|
@@ -658,7 +663,6 @@ class Combination extends AudioCalibrator {
|
|
|
658
663
|
dL_n: this.dL_n,
|
|
659
664
|
})
|
|
660
665
|
.then(res => {
|
|
661
|
-
if (this.numSuccessfulCaptured < this.numCaptures) {
|
|
662
666
|
this.numSuccessfulCaptured += 2;
|
|
663
667
|
this.stepNum += 1;
|
|
664
668
|
console.log('got impulse response ' + this.stepNum);
|
|
@@ -670,7 +674,6 @@ class Combination extends AudioCalibrator {
|
|
|
670
674
|
message: this.status,
|
|
671
675
|
});
|
|
672
676
|
return res['ir'];
|
|
673
|
-
}
|
|
674
677
|
})
|
|
675
678
|
.catch(err => {
|
|
676
679
|
console.error(err);
|
|
@@ -735,6 +738,7 @@ class Combination extends AudioCalibrator {
|
|
|
735
738
|
'Waiting ' + this._calibrateSoundBackgroundSecs + ' second(s) to record background noise'
|
|
736
739
|
);
|
|
737
740
|
let time_to_wait = this._calibrateSoundBackgroundSecs + 0.5;
|
|
741
|
+
this.addTimeStamp(`Record ${time_to_wait.toFixed(1)} s of background.`)
|
|
738
742
|
await sleep(time_to_wait);
|
|
739
743
|
};
|
|
740
744
|
|
|
@@ -779,7 +783,7 @@ class Combination extends AudioCalibrator {
|
|
|
779
783
|
*/
|
|
780
784
|
#afterMLSRecord = async () => {
|
|
781
785
|
console.log('after record');
|
|
782
|
-
this.addTimeStamp(`After record unfiltered
|
|
786
|
+
this.addTimeStamp(`After record unfiltered MLS version ${this.icapture}`);
|
|
783
787
|
await this.sendRecordingToServerForProcessing();
|
|
784
788
|
};
|
|
785
789
|
|
|
@@ -1021,7 +1025,7 @@ class Combination extends AudioCalibrator {
|
|
|
1021
1025
|
let knownGain = this.oldComponentIR.Gain;
|
|
1022
1026
|
let knownFreq = this.oldComponentIR.Freq;
|
|
1023
1027
|
let sampleRate = this.sourceSamplingRate || 96000;
|
|
1024
|
-
this.addTimeStamp('Get PSD of
|
|
1028
|
+
this.addTimeStamp('Get PSD of MLS recording');
|
|
1025
1029
|
if (this.isCalibrating) return null;
|
|
1026
1030
|
let component_unconv_rec_psd = await this.pyServerAPI
|
|
1027
1031
|
.getSubtractedPSDWithRetry(unconv_rec, knownGain, knownFreq, sampleRate)
|
|
@@ -1114,7 +1118,7 @@ class Combination extends AudioCalibrator {
|
|
|
1114
1118
|
//iir w/ and without bandpass psd. done
|
|
1115
1119
|
unconv_rec = this.componentInvertedImpulseResponseNoBandpass;
|
|
1116
1120
|
conv_rec = this.componentInvertedImpulseResponse;
|
|
1117
|
-
this.addTimeStamp('Get PSD of component
|
|
1121
|
+
this.addTimeStamp('Get PSD of component IIR and component IIR no band pass');
|
|
1118
1122
|
if (this.isCalibrating) return null;
|
|
1119
1123
|
let component_iir_psd = await this.pyServerAPI
|
|
1120
1124
|
.getPSDWithRetry({
|
|
@@ -1135,7 +1139,7 @@ class Combination extends AudioCalibrator {
|
|
|
1135
1139
|
});
|
|
1136
1140
|
unconv_rec = this.systemInvertedImpulseResponseNoBandpass;
|
|
1137
1141
|
conv_rec = this.systemInvertedImpulseResponse;
|
|
1138
|
-
this.addTimeStamp('Get PSD of system
|
|
1142
|
+
this.addTimeStamp('Get PSD of system IIR and system IIR no band pass');
|
|
1139
1143
|
if (this.isCalibrating) return null;
|
|
1140
1144
|
let system_iir_psd = await this.pyServerAPI
|
|
1141
1145
|
.getPSDWithRetry({
|
|
@@ -1155,7 +1159,7 @@ class Combination extends AudioCalibrator {
|
|
|
1155
1159
|
console.error(err);
|
|
1156
1160
|
});
|
|
1157
1161
|
|
|
1158
|
-
this.addTimeStamp('Get PSD of
|
|
1162
|
+
this.addTimeStamp('Get PSD of MLS sequence');
|
|
1159
1163
|
if (this.isCalibrating) return null;
|
|
1160
1164
|
let mls_psd = await this.pyServerAPI
|
|
1161
1165
|
.getMLSPSDWithRetry({
|
|
@@ -1174,7 +1178,7 @@ class Combination extends AudioCalibrator {
|
|
|
1174
1178
|
console.error(err);
|
|
1175
1179
|
});
|
|
1176
1180
|
|
|
1177
|
-
this.addTimeStamp('Get PSD of
|
|
1181
|
+
this.addTimeStamp('Get PSD of filtered MLS (system)');
|
|
1178
1182
|
if (this.isCalibrating) return null;
|
|
1179
1183
|
let system_filtered_mls_psd = await this.pyServerAPI
|
|
1180
1184
|
.getMLSPSDWithRetry({
|
|
@@ -1210,7 +1214,7 @@ class Combination extends AudioCalibrator {
|
|
|
1210
1214
|
console.error(err);
|
|
1211
1215
|
});
|
|
1212
1216
|
|
|
1213
|
-
this.addTimeStamp('Get PSD of
|
|
1217
|
+
this.addTimeStamp('Get PSD of filtered MLS (component)');
|
|
1214
1218
|
if (this.isCalibrating) return null;
|
|
1215
1219
|
let component_filtered_mls_psd = await this.pyServerAPI
|
|
1216
1220
|
.getMLSPSDWithRetry({
|
|
@@ -1405,7 +1409,7 @@ class Combination extends AudioCalibrator {
|
|
|
1405
1409
|
let knownGain = this.oldComponentIR.Gain;
|
|
1406
1410
|
let knownFreq = this.oldComponentIR.Freq;
|
|
1407
1411
|
let sampleRate = this.sourceSamplingRate || 96000;
|
|
1408
|
-
this.addTimeStamp('Get PSD of
|
|
1412
|
+
this.addTimeStamp('Get PSD of MLS recording');
|
|
1409
1413
|
if (this.isCalibrating) return null;
|
|
1410
1414
|
let unconv_results = await this.pyServerAPI
|
|
1411
1415
|
.getSubtractedPSDWithRetry(unconv_rec, knownGain, knownFreq, sampleRate)
|
|
@@ -1472,7 +1476,7 @@ class Combination extends AudioCalibrator {
|
|
|
1472
1476
|
|
|
1473
1477
|
unconv_rec = this.componentInvertedImpulseResponseNoBandpass;
|
|
1474
1478
|
conv_rec = this.componentInvertedImpulseResponse;
|
|
1475
|
-
this.addTimeStamp('Get PSD of component
|
|
1479
|
+
this.addTimeStamp('Get PSD of component IIR and component IIR no bandpass');
|
|
1476
1480
|
if (this.isCalibrating) return null;
|
|
1477
1481
|
let component_iir_psd = await this.pyServerAPI
|
|
1478
1482
|
.getPSDWithRetry({
|
|
@@ -1493,7 +1497,7 @@ class Combination extends AudioCalibrator {
|
|
|
1493
1497
|
});
|
|
1494
1498
|
unconv_rec = this.systemInvertedImpulseResponseNoBandpass;
|
|
1495
1499
|
conv_rec = this.systemInvertedImpulseResponse;
|
|
1496
|
-
this.addTimeStamp('Get PSD of system
|
|
1500
|
+
this.addTimeStamp('Get PSD of system IIR and system IIR no bandpass');
|
|
1497
1501
|
if (this.isCalibrating) return null;
|
|
1498
1502
|
let system_iir_psd = await this.pyServerAPI
|
|
1499
1503
|
.getPSDWithRetry({
|
|
@@ -1513,7 +1517,7 @@ class Combination extends AudioCalibrator {
|
|
|
1513
1517
|
console.error(err);
|
|
1514
1518
|
});
|
|
1515
1519
|
|
|
1516
|
-
this.addTimeStamp('Get PSD of
|
|
1520
|
+
this.addTimeStamp('Get PSD of MLS sequence');
|
|
1517
1521
|
if (this.isCalibrating) return null;
|
|
1518
1522
|
let mls_psd = await this.pyServerAPI
|
|
1519
1523
|
.getMLSPSDWithRetry({
|
|
@@ -1532,7 +1536,7 @@ class Combination extends AudioCalibrator {
|
|
|
1532
1536
|
console.error(err);
|
|
1533
1537
|
});
|
|
1534
1538
|
|
|
1535
|
-
this.addTimeStamp('Get PSD of filtered
|
|
1539
|
+
this.addTimeStamp('Get PSD of filtered MLS (component)');
|
|
1536
1540
|
if (this.isCalibrating) return null;
|
|
1537
1541
|
let filtered_mls_psd = await this.pyServerAPI
|
|
1538
1542
|
.getMLSPSDWithRetry({
|
|
@@ -1679,7 +1683,7 @@ class Combination extends AudioCalibrator {
|
|
|
1679
1683
|
//iir w/ and without bandpass psd
|
|
1680
1684
|
unconv_rec = this.componentInvertedImpulseResponseNoBandpass;
|
|
1681
1685
|
conv_rec = this.componentInvertedImpulseResponse;
|
|
1682
|
-
this.addTimeStamp('Get PSD of component
|
|
1686
|
+
this.addTimeStamp('Get PSD of component IIR and component IIR no band pass');
|
|
1683
1687
|
if (this.isCalibrating) return null;
|
|
1684
1688
|
let component_iir_psd = await this.pyServerAPI
|
|
1685
1689
|
.getPSDWithRetry({
|
|
@@ -1700,7 +1704,7 @@ class Combination extends AudioCalibrator {
|
|
|
1700
1704
|
});
|
|
1701
1705
|
unconv_rec = this.systemInvertedImpulseResponseNoBandpass;
|
|
1702
1706
|
conv_rec = this.systemInvertedImpulseResponse;
|
|
1703
|
-
this.addTimeStamp('Get PSD of system
|
|
1707
|
+
this.addTimeStamp('Get PSD of system IIR and system IIR no band pass');
|
|
1704
1708
|
if (this.isCalibrating) return null;
|
|
1705
1709
|
let system_iir_psd = await this.pyServerAPI
|
|
1706
1710
|
.getPSDWithRetry({
|
|
@@ -1720,7 +1724,7 @@ class Combination extends AudioCalibrator {
|
|
|
1720
1724
|
console.error(err);
|
|
1721
1725
|
});
|
|
1722
1726
|
|
|
1723
|
-
this.addTimeStamp('Get PSD of
|
|
1727
|
+
this.addTimeStamp('Get PSD of MLS sequence');
|
|
1724
1728
|
if (this.isCalibrating) return null;
|
|
1725
1729
|
let mls_psd = await this.pyServerAPI
|
|
1726
1730
|
.getMLSPSDWithRetry({
|
|
@@ -1739,7 +1743,7 @@ class Combination extends AudioCalibrator {
|
|
|
1739
1743
|
console.error(err);
|
|
1740
1744
|
});
|
|
1741
1745
|
|
|
1742
|
-
this.addTimeStamp('Get PSD of filtered
|
|
1746
|
+
this.addTimeStamp('Get PSD of filtered MLS (system)');
|
|
1743
1747
|
if (this.isCalibrating) return null;
|
|
1744
1748
|
let filtered_mls_psd = await this.pyServerAPI
|
|
1745
1749
|
.getMLSPSDWithRetry({
|
|
@@ -1910,7 +1914,7 @@ class Combination extends AudioCalibrator {
|
|
|
1910
1914
|
|
|
1911
1915
|
const amplitude = Math.pow(10, this.power_dB / 20);
|
|
1912
1916
|
//MLSpower = Math.pow(10,this.power_dB/20);
|
|
1913
|
-
this.addTimeStamp('
|
|
1917
|
+
this.addTimeStamp('Compute MLS sequence');
|
|
1914
1918
|
if (this.isCalibrating) return null;
|
|
1915
1919
|
await this.pyServerAPI
|
|
1916
1920
|
.getMLSWithRetry({
|
|
@@ -2255,9 +2259,11 @@ class Combination extends AudioCalibrator {
|
|
|
2255
2259
|
|
|
2256
2260
|
#playCalibrationAudioVolume = async () => {
|
|
2257
2261
|
if (this.numCalibratingRoundsCompleted==1) {
|
|
2258
|
-
this.recordingChecks['warnings'].push(`Redo 1000 Hz, ${this.inDB} dB, recording because SD ${this.recordingChecks['volume'][this.inDB]['sd']} dB> ${this.calibrateSound1000HzMaxSD_dB} dB`);
|
|
2262
|
+
this.recordingChecks['warnings'].push(`Redo 1000 Hz, ${this.inDB} dB, recording because SD ${(this.recordingChecks['volume'][this.inDB]['sd'])} dB> ${this.calibrateSound1000HzMaxSD_dB} dB`);
|
|
2259
2263
|
this.status =
|
|
2260
|
-
`Redoing 1000 Hz recording because SD
|
|
2264
|
+
`Redoing 1000 Hz recording because SD
|
|
2265
|
+
${this.recordingChecks['volume'][this.inDB]['sd']} dB>
|
|
2266
|
+
${this.calibrateSound1000HzMaxSD_dB} dB`.toString() +
|
|
2261
2267
|
this.generateTemplate().toString();
|
|
2262
2268
|
this.emit('update', {
|
|
2263
2269
|
message: this.status,
|
|
@@ -2280,7 +2286,10 @@ class Combination extends AudioCalibrator {
|
|
|
2280
2286
|
|
|
2281
2287
|
#sendToServerForProcessing = async lCalib => {
|
|
2282
2288
|
console.log('Sending data to server');
|
|
2283
|
-
this.
|
|
2289
|
+
const total_dur = this.calibrateSound1000HzPreSec + this.calibrateSound1000HzSec + this.calibrateSound1000HzPostSec;
|
|
2290
|
+
this.addTimeStamp(`Record ${total_dur.toFixed(1)} s of 1000 Hz at ${this.inDB} dB.
|
|
2291
|
+
(${this.calibrateSound1000HzPreSec.toFixed(1)} s pre + ${this.calibrateSound1000HzSec.toFixed(1)}
|
|
2292
|
+
s used + ${this.calibrateSound1000HzPostSec.toFixed(1)} s post) ”`);
|
|
2284
2293
|
let left = this.calibrateSound1000HzPreSec;
|
|
2285
2294
|
let right = this.calibrateSound1000HzPreSec + this.calibrateSound1000HzSec;
|
|
2286
2295
|
if (this.isCalibrating) return null;
|
|
@@ -2301,18 +2310,22 @@ class Combination extends AudioCalibrator {
|
|
|
2301
2310
|
.catch(err => {
|
|
2302
2311
|
console.warn(err);
|
|
2303
2312
|
});
|
|
2304
|
-
|
|
2305
|
-
|
|
2306
|
-
.
|
|
2307
|
-
|
|
2308
|
-
|
|
2309
|
-
|
|
2310
|
-
|
|
2311
|
-
|
|
2312
|
-
|
|
2313
|
-
|
|
2314
|
-
|
|
2315
|
-
|
|
2313
|
+
const rec = this.getLastVolumeRecordedSignal();
|
|
2314
|
+
console.log('pre period power: ', getPower(rec.slice(0,this.calibrateSound1000HzPreSec * this.sourceSamplingRate)).toFixed(1));
|
|
2315
|
+
console.log('pre period power: ',
|
|
2316
|
+
getPower(rec.slice(
|
|
2317
|
+
this.calibrateSound1000HzPreSec * this.sourceSamplingRate,
|
|
2318
|
+
(this.calibrateSound1000HzPreSec + this.calibrateSound1000HzSec)* this.sourceSamplingRate)).toFixed(1));
|
|
2319
|
+
console.log('pre period power: ', getPower(rec.slice(
|
|
2320
|
+
(this.calibrateSound1000HzPreSec + this.calibrateSound1000HzSec)* this.sourceSamplingRate)).toFixed(1));
|
|
2321
|
+
const res = volumePowerCheck(
|
|
2322
|
+
rec,
|
|
2323
|
+
this.sourceSamplingRate || 96000,
|
|
2324
|
+
this.calibrateSound1000HzPreSec,
|
|
2325
|
+
this.calibrateSound1000HzSec,
|
|
2326
|
+
this._calibrateSoundPowerBinDesiredSec);
|
|
2327
|
+
console.log(res);
|
|
2328
|
+
this.recordingChecks['volume'][this.inDB] = res;
|
|
2316
2329
|
};
|
|
2317
2330
|
|
|
2318
2331
|
startCalibrationVolume = async (stream, gainValues, lCalib, componentGainDBSPL) => {
|
|
@@ -2358,7 +2371,6 @@ class Combination extends AudioCalibrator {
|
|
|
2358
2371
|
//reset the values
|
|
2359
2372
|
//this.incrementStatusBar();
|
|
2360
2373
|
|
|
2361
|
-
console.log(this.recordingChecks['warnings']);
|
|
2362
2374
|
this.outDBSPL = null;
|
|
2363
2375
|
this.outDBSPL = null;
|
|
2364
2376
|
this.outDBSPL1000 = null;
|
|
@@ -2394,7 +2406,7 @@ class Combination extends AudioCalibrator {
|
|
|
2394
2406
|
gainValues[i],
|
|
2395
2407
|
lCalib, //todo make this a class parameter
|
|
2396
2408
|
checkRec,
|
|
2397
|
-
() => {return this.recordingChecks['volume'][this.inDB]['sd']},
|
|
2409
|
+
() => {return this.recordingChecks?.['volume']?.[this.inDB]?.['sd'] || 0},
|
|
2398
2410
|
this.calibrateSound1000HzMaxSD_dB
|
|
2399
2411
|
);
|
|
2400
2412
|
} while (this.outDBSPL === null);
|
|
@@ -2408,7 +2420,7 @@ class Combination extends AudioCalibrator {
|
|
|
2408
2420
|
}
|
|
2409
2421
|
if (this.isCalibrating) return null;
|
|
2410
2422
|
// get the volume calibration parameters from the server
|
|
2411
|
-
this.addTimeStamp('Get
|
|
2423
|
+
this.addTimeStamp('Get sound calibration parameters');
|
|
2412
2424
|
|
|
2413
2425
|
const parameters = await this.pyServerAPI
|
|
2414
2426
|
.getVolumeCalibrationParameters({
|