Browse Source

Enables LocalStatsCollector for the local audio levels instead of rtp stats. Fixes issue with local audio level calculations.

master
hristoterezov 11 years ago
parent
commit
83b4ee96d3
3 changed files with 67 additions and 47 deletions
  1. 16
    33
      app.js
  2. 49
    12
      local_stats.js
  3. 2
    2
      rtp_stats.js

+ 16
- 33
app.js View File

@@ -445,33 +445,23 @@ function muteVideo(pc, unmute) {
445 445
 }
446 446
 
447 447
 /**
448
- * Callback called by {@link StatsCollector} in intervals supplied to it's
449
- * constructor.
450
- * @param statsCollector {@link StatsCollector} source of the event.
448
+ * Callback for audio levels changed.
449
+ * @param jid JID of the user
450
+ * @param audioLevel the audio level value
451 451
  */
452
-function statsUpdated(statsCollector)
452
+function audioLevelUpdated(jid, audioLevel)
453 453
 {
454
-    Object.keys(statsCollector.jid2stats).forEach(function (jid)
454
+    var resourceJid;
455
+    if(jid === LocalStatsCollector.LOCAL_JID)
455 456
     {
456
-        var peerStats = statsCollector.jid2stats[jid];
457
-        Object.keys(peerStats.ssrc2AudioLevel).forEach(function (ssrc)
458
-        {
459
-            AudioLevels.updateAudioLevel(   Strophe.getResourceFromJid(jid),
460
-                                            peerStats.ssrc2AudioLevel[ssrc]);
461
-        });
462
-    });
463
-}
457
+        resourceJid = AudioLevels.LOCAL_LEVEL;
458
+    }
459
+    else
460
+    {
461
+        resourceJid = Strophe.getResourceFromJid(jid);
462
+    }
464 463
 
465
-/**
466
- * Callback called by {@link LocalStatsCollector} in intervals supplied to it's
467
- * constructor.
468
- * @param statsCollector {@link LocalStatsCollector} source of the event.
469
- */
470
-function localStatsUpdated(statsCollector)
471
-{
472
-    AudioLevels.updateAudioLevel(
473
-            AudioLevels.LOCAL_LEVEL,
474
-            statsCollector.audioLevel);
464
+    AudioLevels.updateAudioLevel(resourceJid, audioLevel);
475 465
 }
476 466
 
477 467
 /**
@@ -483,10 +473,7 @@ function startRtpStatsCollector()
483 473
     if (config.enableRtpStats)
484 474
     {
485 475
         statsCollector = new StatsCollector(
486
-            getConferenceHandler().peerconnection, 200, statsUpdated);
487
-
488
-        stopLocalRtpStatsCollector();
489
-
476
+            getConferenceHandler().peerconnection, 200, audioLevelUpdated);
490 477
         statsCollector.start();
491 478
     }
492 479
 }
@@ -511,7 +498,7 @@ function startLocalRtpStatsCollector(stream)
511 498
 {
512 499
     if(config.enableRtpStats)
513 500
     {
514
-        localStatsCollector = new LocalStatsCollector(stream, 200, localStatsUpdated);
501
+        localStatsCollector = new LocalStatsCollector(stream, 100, audioLevelUpdated);
515 502
         localStatsCollector.start();
516 503
     }
517 504
 }
@@ -1123,11 +1110,7 @@ function disposeConference(onUnload) {
1123 1110
         handler.peerconnection.close();
1124 1111
     }
1125 1112
     stopRTPStatsCollector();
1126
-    if(!onUnload) {
1127
-        startLocalRtpStatsCollector(connection.jingle.localAudio);
1128
-    }
1129
-    else
1130
-    {
1113
+    if(onUnload) {
1131 1114
         stopLocalRtpStatsCollector();
1132 1115
     }
1133 1116
     focus = null;

+ 49
- 12
local_stats.js View File

@@ -6,13 +6,13 @@ var LocalStatsCollector = (function() {
6 6
      * Size of the webaudio analizer buffer.
7 7
      * @type {number}
8 8
      */
9
-    var WEBAUDIO_ANALIZER_FFT_SIZE = 512;
9
+    var WEBAUDIO_ANALIZER_FFT_SIZE = 2048;
10 10
 
11 11
     /**
12 12
      * Value of the webaudio analizer smoothing time parameter.
13 13
      * @type {number}
14 14
      */
15
-    var WEBAUDIO_ANALIZER_SMOOTING_TIME = 0.1;
15
+    var WEBAUDIO_ANALIZER_SMOOTING_TIME = 0.8;
16 16
 
17 17
     /**
18 18
      * <tt>LocalStatsCollector</tt> calculates statistics for the local stream.
@@ -54,12 +54,16 @@ var LocalStatsCollector = (function() {
54 54
         this.intervalId = setInterval(
55 55
             function () {
56 56
                 var array = new Uint8Array(analyser.frequencyBinCount);
57
-                analyser.getByteFrequencyData(array);
58
-                self.audioLevel = FrequencyDataToAudioLevel(array);
59
-                self.updateCallback(self);
57
+                analyser.getByteTimeDomainData(array);
58
+                var audioLevel = TimeDomainDataToAudioLevel(array);
59
+                if(audioLevel != self.audioLevel) {
60
+                    self.audioLevel = animateLevel(audioLevel, self.audioLevel);
61
+                    self.updateCallback(LocalStatsCollectorProto.LOCAL_JID, self.audioLevel);
62
+                }
60 63
             },
61 64
             this.intervalMilis
62 65
         );
66
+
63 67
     };
64 68
 
65 69
     /**
@@ -73,22 +77,55 @@ var LocalStatsCollector = (function() {
73 77
     };
74 78
 
75 79
     /**
76
-     * Converts frequency data array to audio level.
77
-     * @param array the frequency data array.
80
+     * Converts time domain data array to audio level.
81
+     * @param array the time domain data array.
78 82
      * @returns {number} the audio level
79 83
      */
80
-    var FrequencyDataToAudioLevel = function (array) {
84
+    var TimeDomainDataToAudioLevel = function (samples) {
85
+
81 86
         var maxVolume = 0;
82 87
 
83
-        var length = array.length;
88
+        var length = samples.length;
84 89
 
85 90
         for (var i = 0; i < length; i++) {
86
-            if (maxVolume < array[i])
87
-                maxVolume = array[i];
91
+            if (maxVolume < samples[i])
92
+                maxVolume = samples[i];
88 93
         }
89 94
 
90
-        return maxVolume / 255;
95
+        return parseFloat(((maxVolume - 127) / 128).toFixed(3));
91 96
     };
92 97
 
98
+    /**
99
+     * Animates audio level change
100
+     * @param newLevel the new audio level
101
+     * @param lastLevel the last audio level
102
+     * @returns {Number} the audio level to be set
103
+     */
104
+    function animateLevel(newLevel, lastLevel)
105
+    {
106
+        var value = 0;
107
+        var diff = lastLevel - newLevel;
108
+        if(diff > 0.2)
109
+        {
110
+            value = lastLevel - 0.2;
111
+        }
112
+        else if(diff < -0.4)
113
+        {
114
+            value = lastLevel + 0.4;
115
+        }
116
+        else
117
+        {
118
+            value = newLevel;
119
+        }
120
+
121
+        return parseFloat(value.toFixed(3));
122
+    }
123
+
124
+    /**
125
+     * Indicates that this audio level is for local jid.
126
+     * @type {string}
127
+     */
128
+    LocalStatsCollectorProto.LOCAL_JID = 'local';
129
+
93 130
     return LocalStatsCollectorProto;
94 131
 })();

+ 2
- 2
rtp_stats.js View File

@@ -213,6 +213,8 @@ StatsCollector.prototype.processReport = function ()
213 213
             // but it seems to vary between 0 and around 32k.
214 214
             audioLevel = audioLevel / 32767;
215 215
             jidStats.setSsrcAudioLevel(ssrc, audioLevel);
216
+            if(jid != connection.emuc.myroomjid)
217
+                this.updateCallback(jid, audioLevel);
216 218
         }
217 219
 
218 220
         var key = 'packetsReceived';
@@ -281,7 +283,5 @@ StatsCollector.prototype.processReport = function ()
281 283
         // bar indicator
282 284
         //console.info("Loss SMA3: " + outputAvg + " Q: " + quality);
283 285
     }
284
-
285
-    self.updateCallback(self);
286 286
 };
287 287
 

Loading…
Cancel
Save