Я хочу смешать два (или более) 16-битных аудиопотока, используя OpenGL, и мне нужна небольшая помощь
По сути, я хочу поместить аудио данные в текстуру, которую я рисую в кадреобъект буфера, а затем прочитать обратно.Это не проблема, однако рисование данных таким образом, чтобы получить правильные результаты, немного более проблематично.
У меня есть два основных вопроса.
- Чтобы смешать данные с помощьюрисование мне нужно использовать смешивание (альфа = 0,5), однако результат не должен иметь альфа-канал.Так что, если я выполню рендеринг, например, в буфер кадров с форматом RGB, альфа-смешение все еще будет работать, как я ожидаю, и полученная альфа не будет записана в fbo?(Я хочу избежать необходимости читать fbo для каждого прохода рендеринга)
текстура | sR | sG | sB |
framebuffer (перед) | dR | dG| дБ |
кадровый буфер (после) | дР * 0,5 + сР * 0,5 | дГ * 0,5 + сГ * 0,5 | дБ * 0,5 + сБ * 0,5 |
- Аудио сэмплы имеют 16-битные целые значения со знаком.Можно ли сделать так подписанные расчеты?Или мне нужно будет сначала преобразовать значения в unsigned на процессоре, нарисовать их, а затем сделать их снова подписанными на процессоре?
РЕДАКТИРОВАТЬ:
Мне было немного неясно,Мое оборудование ограничено оборудованием OpenGL 3.3.Я бы предпочел не использовать CUDA или OpenCL, поскольку я уже использую OpenGL для других вещей.
Каждый аудиосэмпл будет воспроизводиться в отдельных проходах, что означает, что он должен «смешиваться» с тем, что уже былоотображается в буфер кадра.Проблема заключается в том, как вывод пиксельного шейдера записывается в кадровый буфер (насколько я знаю, это смешивание недоступно через программируемые шейдеры, и нужно использовать glBlendFunc).
EDIT2:
Каждый аудиосэмпл будет воспроизводиться с разными проходами, поэтому в шейдере одновременно будет доступен только один аудиосэмпл, а это значит, что их нужно накапливать в FBO.
foreach(var audio_sample in audio_samples)
draw(audio_sample);
и не
for(int n = 0; n < audio_samples.size(); ++n)
{
glActiveTexture(GL_TEXTURE0 + n);
glBindTexture(audio_sample);
}
draw_everything();