Open6

OpenALでMIDI音源は作れるのか問題

okuokuokuoku

... まぁぶっちゃけ無理なんですけど。。どこまで迫れるのか問題。

okuokuokuoku

パン

簡単にわかるのはOpenALではMIDI的なパンを表現できないという点。MIDIのパンはステレオが前提であり、 64 でLR同率、0でL、127でRのようなふりわけになっているが、OpenALは3Dオーディオなのでスピーカー単位で音源の位置を指定することができない。

OpenAL is foremost a means to generate audio in a simulated three-dimensional space. Consequently, legacy audio concepts such as panning and left/right channels are not directly supported

本当にマジでスピーカー単位で音源の位置を指定したいのならば、 ステレオサンプルを手動で生成して入力する くらいしか無いんでは。。OpenALではステレオサンプルを入力すると3D的な定位は無視されるようになる。

Buffers containing audio data with more than one channel will be played without 3D spatialization features – these formats are normally used for background music.

OpenAL仕様の書きっぷりからして、BGMの生成は想定していなそうなことがわかる。

okuokuokuoku

波形のループ

OpenALは波形をループすることはできる( AL_LOOPING )が、これはバッファ単位に限られる。よって、波形にループがある場合は、波形データを事前に分割しておきループより前のバッファとループするバッファを別々にenqueueする必要がある。

AL_SOFT_loop_points 拡張は単一バッファ内でループポイントを設定できる。ただしシンセ波形でよくあるピンポンループをこれで実現することはできない。

DLS Level 2ではループを終了しリリース部の波形を再生させる機能がある。OpenALではこれに対応する良い方法が無い。例えばバッファのループに頼らなくても良いように波形を適当に延長し100Hzとかそれ以上の頻度で波形を更新する前提を置けばできる。。かもしれないが聴覚上不味いことにならないかは不安がある。

okuokuokuoku

フィルタ

OpenALの基本仕様にはフィルタは存在しない。このため、ボイスまたはパート毎のLPF/HPFを実現することはできない。例えばEmscriptenのOpenALはエフェクトを一切実装していない。

OpenAL-softはEFXエフェクトスロットを事実上無限に作成でき、 AL_SOFT_effect_target 拡張によってそれらをチェインすることさえ可能なので一般的なシンセサイザのフィルタ要求には応えられる可能性がある。が、EFXエフェクトのパラメーターをアニメーションさせて良いのかが判然としない。

LPF/HPFは一般にbi-quadフィルタで実装されるので長さが短かく、パラメーター変更によるアーティファクトはそこまで無いんじゃないか。。と期待している。

AppleのOpenAL実装は ALC_EXT_ASA としてリバーブやLPFを提供しているが、カットオフ周波数等を直接指定できるわけではないので今回の目的には使用できない可能性が高い。

CreativeのOpenAL実装は、エフェクトスロットを出力全体で4本程度しか使えない。

okuokuokuoku

ピッチ

OpenALにおいて音源のピッチは AL_PITCH で与えられるが、その上限は実装依存としている。

Implementations may clamp the actual output pitch range to any values subject to the implementation's own limits.

例えば、OpenAL-softは元のピッチの10倍までとしている。...まぁ普通の楽器の音域は10オクターブも無いのでこれが問題になることは無いだろう。

https://github.com/kcat/openal-soft/blob/ba0f592715e7a0101bed4c2491c624db8915002d/alc/alu.cpp#L111

また、バッファにはバッファ単位でサンプリング周波数を設定できる。

okuokuokuoku

エンベロープ、LFO

OpenALの仕様にはEGやLFOは無い。このため、適当な周期でタイマ割り込みなりなんなりをして自前でLFO発振なりエンベロープの処理なりを行う必要がある。

経験上は1kHz程度の処理間隔で十分な効果が得られるが、果してOpenALの実装側がこれについてこれるのだろうか。。