Я создал класс SoundEnvelope, чтобы сохранить пару сэмплов «атака-сустейн». Класс также предварительно обрабатывает цикл сустейна для перекрестного затухания с последним выбранным количеством стерео сэмплов блока атаки, и смещение кодера MP3 в 30 мс обрезается для правильного воспроизведения.
Обрезка и зацикливание необходимы для моего проекта.
Теперь атака накапливается нормально, плавно переходит в цикл сустейна, но в конце цикл, похоже, пропускает некоторые данные, и, похоже, он в основном связан с эффектом перекрестного затухания, вероятно, это проблема синхронизации, но я просто не могу найти проблему.
Для тех, кто не знаком с динамически обработанными звуками, вот функция , я использую цикл с вилкой if-else, чтобы решить, идет ли чанк в атаку или переменная сустейна моего экземпляра SoundEnvelope.
[ОБНОВЛЕНИЕ]
@A Shelly:
Звуковая огибающая в профессиональном синтезаторе состоит из последовательности атака-затухание-выдержка-релиз. В моем случае атака и затухание - это одна и та же часть, и релиз просто затухает в объеме сустейна, который должен плавно возвращаться в себя.
Допустим, у нас есть необработанный образец трубы, который выглядит как tfweeeewweeeewweeeewweeeep , а мой экстракт состоит из _a
= [tfweeeew] и _s
= [ weeeewweeeewwe] порций. Теперь это может быть любой образец, и я использую здесь унифицированную 0,5-секундную атаку и 1,0-секундную петлю сустейна. Поэтому, чтобы он звучал непрерывно, мне нужно постепенно затенять конец цикла, поскольку он не совпадает с собственным началом, и одновременно затухать в концевой части части атаки, что позволило бы бесшовно перемешать образец. Конечно, это может привести к легкому дыханию в конечной точке сэмпла, но это все же лучше, чем при его цикличном всплытии, например ... deewdeewdeewdeewdeew ...
[КОД]
Вот функция зацикливания, я действительно надеюсь, что кто-то может мне помочь, заранее спасибо:
public function fadeLoop(fadeStereoSamples:uint):void {
var volume:Number;
var helper:ByteArray = new ByteArray();
var fade:Number;
// moves the pointer to the overlapping part's beginning of sustain and attack ByteArrays
// _a and _s are the two chunk arrays in the SoundEnvelope object
_a.position = _a.length - fadeStereoSamples * 8;
_s.position = _s.length - fadeStereoSamples * 8;
// crossfade through input amount of sample-pairs
for (var i:uint = 0; i < fadeStereoSamples; i++) {
fade = i / fadeStereoSamples;
// fadestep left
helper.writeFloat(_a.readFloat() * fade + _s.readFloat() * (1 - fade));
// fadestep right
helper.writeFloat(_a.readFloat() * fade + _s.readFloat() * (1 - fade));
}
_s.position = _s.length - fadeStereoSamples * 8;
for (i = 0; i < fadeStereoSamples; i++) {
helper.position = 0;
_s.writeFloat(helper.readFloat());
_s.writeFloat(helper.readFloat());
}
_a.position = 0;
_s.position = 0;
}