С моей точки зрения, у вас есть два варианта; иметь громкость всех звуковых файлов вашей игры , нормализованную до одного и того же уровня (выровненный, сжатый, ограниченный и т. д.), или, если доступно, вы можете использовать webaudio api для создания ограничителя и подключите его к источнику звука.
Вариант 1: нормализация громкости
Нормализация громкости означает, что средняя громкость вашего звука должна быть определенной, это означает, что ваш аудиофайл будет иметь уровень громкости, транспонированный для соответствия средней громкости вашим требованиям. Проще говоря, он будет уменьшать или увеличивать громкость, чтобы довести звук до требуемого уровня. Если вы доведите громкость всех своих треков до определенного уровня, они обязательно останутся в определенном диапазоне громкости.
Это можно сделать с помощью программного обеспечения для нормализации звука, википедия предлагает ReplayGain , Проверка звука и EBU R128 ; но вы можете найти других, погуглив на это.
Вариант 2: Ограничитель Webaudio с использованием DynamicsCompressorNode
Если вы можете использовать webaudio api в своем коде, используйте простой ограничитель . Конечно, существует множество различных типов ограничителей, но я не намерен обсуждать различия и преимущества каждого из них.
Это можно сделать, подключив источник звука, подключенный к узлу DynamicsCompressorNode.
Я нашел этот блог, который немного глубже вписывается в ограничитель на webaudio , и ниже приведен фрагмент, который я взял из блога о том, как построить ограничитель с узлом динамического компрессора.
var context = new AudioContext();
var audio = document.getElementById('audio');
var label = document.getElementById('maximize-db');
var reduction = document.getElementById('reduction');
var source = context.createMediaElementSource(audio);
var preGain = context.createGain();
var limiter = context.createDynamicsCompressor();
limiter.threshold.value = 0.0; // this is the pitfall, leave some headroom
limiter.knee.value = 0.0; // brute force
limiter.ratio.value = 20.0; // max compression
limiter.attack.value = 0.005; // 5ms attack
limiter.release.value = 0.050; // 50ms release
source.connect(preGain);
preGain.connect(limiter);
limiter.connect(context.destination);
var dbToGain = function(db) {
return Math.exp(db * Math.log(10.0) / 20.0);
}
var maximize = (function(db) {
preGain.gain.value = dbToGain(db);
label.textContent = db;
return arguments.callee;
})(0);
var showReduction = (function() {
reduction.style.width = (dbToGain(limiter.reduction.value) * 288) + "px";
window.requestAnimationFrame(arguments.callee);
})();
html, body {
font-size: 12px;
font-family: "Open Sans";
background: white;
}
.controls {
padding: 6px 16px;
border-radius: 5px;
background: #424242;
color: #f0f0f0;
display: inline-block;
width: 288px;
white-space: nowrap;
}
.controls input {
width: 200px;
}
.controls span, .controls input {
vertical-align: middle;
padding: 0;
margin: 0;
}
#reduction {
margin-top: 4px;
margin-bottom: 2px;
width: 288px;
height: 2px;
background: green;
}
a {
text-decoration: none;
color: #666;
}
p {
color: #CCC;
}
audio {
width: 320px;
}
<h1>Web Audio HardLimiter</h1>
<div class="controls">
<span>Maximize</span>
<input type="range" value="0" step="1" min="0" max="12" oninput="maximize(this.value);">
<span class="value" id="maximize-db">6</span> <span class="unit">dB</span>
<div id="reduction"></div>
</div>
<div>
<h3><a href="http://www.audiotool.com/track/never-ending_passion/" target="audiotool">Never-ending Passion</a> by The Three Pauls</h3>
<audio id="audio" crossorigin controls>
<source src="http://api.audiotool.com/track/never-ending_passion/play.ogg" type="audio/ogg">
<source src="http://api.audiotool.com/track/never-ending_passion/play.mp3" type="audio/mpeg">
Your browser does not support the audio tag.
</audio>
</div>
<p>Does not work in Safari.</p>