Справка с функцией сжатия динамического диапазона (аудио)

Я пишу функцию C# для того, чтобы сделать сжатие динамического диапазона (звуковой эффект, который в основном давит переходный процесс, достигает максимума и усиливает все остальное для создания полного, громче звучат). Я записал функцию, которая делает это (я думаю):

сопроводительный текст http://www.freeimagehosting.net/uploads/feea390f84.jpg

public static void Compress(ref short[] input, double thresholdDb, double ratio)
{
    double maxDb = thresholdDb - (thresholdDb / ratio);
    double maxGain = Math.Pow(10, -maxDb / 20.0);

    for (int i = 0; i < input.Length; i += 2)
    {
        // convert sample values to ABS gain and store original signs
        int signL = input[i] < 0 ? -1 : 1;
        double valL = (double)input[i] / 32768.0;
        if (valL < 0.0)
        {
            valL = -valL;
        }
        int signR = input[i + 1] < 0 ? -1 : 1;
        double valR = (double)input[i + 1] / 32768.0;
        if (valR < 0.0)
        {
            valR = -valR;
        }

        // calculate mono value and compress
        double val = (valL + valR) * 0.5;
        double posDb = -Math.Log10(val) * 20.0;
        if (posDb < thresholdDb)
        {
            posDb = thresholdDb - ((thresholdDb - posDb) / ratio);
        }

        // measure L and R sample values relative to mono value
        double multL = valL / val;
        double multR = valR / val;

        // convert compressed db value to gain and amplify
        val = Math.Pow(10, -posDb / 20.0);
        val = val / maxGain;

        // re-calculate L and R gain values relative to compressed/amplified
        // mono value
        valL = val * multL;
        valR = val * multR;

        double lim = 1.5; // determined by experimentation, with the goal
            // being that the lines below should never (or rarely) be hit
        if (valL > lim)
        {
            valL = lim;
        }
        if (valR > lim)
        {
            valR = lim;
        }

        double maxval = 32000.0 / lim; 

        // convert gain values back to sample values
        input[i] = (short)(valL * maxval); 
        input[i] *= (short)signL;
        input[i + 1] = (short)(valR * maxval); 
        input[i + 1] *= (short)signR;
    }
}

и я называю его с threshold значения между 10,0 дб и 30,0 дб и отношения между 1,5 и 4.0. Эта функция определенно производит более громкий полный звук, но с недопустимым уровнем искажения, даже в низких пороговых значениях и низких отношениях.

Кто-либо может видеть что-то не так с этой функцией? Я обрабатываю аспект стерео правильно (функция принимает стереовход)? Поскольку я (смутно) понимаю вещи, я не хочу сжимать эти два канала отдельно, таким образом, мой код пытается сжать "виртуальное" моно демонстрационное значение и затем применить ту же степень сжатия к L и демонстрационному значению R отдельно. Не уверенный я делаю его правильно, как бы то ни было.

Я думаю, что часть проблемы может "твердое колено" моей функции, которая ударяет сжатие резко, когда порог пересечен. Я думаю, что я, возможно, должен использовать "мягкое колено" как это:

сопроводительный текст http://www.freeimagehosting.net/uploads/4c1040fda8.jpg

Кто-либо может предложить, чтобы модификация моей функции произвела мягкую кривую колена?

6
задан MusiGenesis 26 May 2010 в 03:17
поделиться

2 ответа

Я думаю, что ваше базовое понимание того, как выполнять сжатие, неверно (извините;)). Речь идет не о «сжатии» отдельных значений выборки; это радикально изменит форму волны и вызовет серьезные гармонические искажения. Вам нужно оценить громкость входного сигнала по множеству отсчетов (мне нужно было бы поискать в Google правильную формулу) и использовать это, чтобы применить к входным отсчетам множитель с гораздо более постепенным изменением, чтобы сгенерировать результат.

Форум DSP на kvraudio.com/forum может указать вам правильное направление, если вам трудно найти обычные методы.

1
ответ дан 17 December 2019 в 18:10
поделиться

Проект с открытым исходным кодом Skype Voice Changer включает порт на C# нескольких хороших компрессоров, написанных Scott Stillwell, все с настраиваемыми параметрами:

Первый, похоже, имеет возможность делать soft-knee, хотя параметр для этого не раскрыт.

2
ответ дан 17 December 2019 в 18:10
поделиться
Другие вопросы по тегам:

Похожие вопросы: