読者です 読者をやめる 読者になる 読者になる

shingoushori's dialy

音信号処理を専ら研究していた元博士後期課程の学生によるメモ

Web Audio API で、Multi-tap Delay (3 tap feedforward and 3 tap feedback)

HTML5 JavaScript Web Audio API エフェクタ / Stompbox 信号処理 / Signal Processing

Web Audio APIで、ディレイを組んでみました。
ただ、1本だけディレイのラインを出すだけならば、Web Audio APIにあったはず。
マルチタップで混沌とするには、1本だけのを組み合わせるのはメモリが勿体無い。
ちょっとだけ頭を捻って、1本だけのを組み合わせるよりはエコなものを組みました。

図などは、また時間があるときに描くことにいたしまして ... 

核心は、Web Audio API のフレームの倍サイズのメモリを1本用意し、
各サンプルでの数値をそのメモリ内の2箇所ずつに書き込んでいくこと。
リングバッファの実装で行われている技法です。
さっと探して参考文献が見当たらなかったので、こちらも後日。

計算量を検討したわけじゃないですが、
Web Audio APIのようにザクザクとブロック処理する場合は、
毎サンプルごとにリードライトを繰り返すくらいなら、
2箇所に書いてしまって、ポインタだけを動かした方が、たぶんシンプルです。

 

そんなMulti-tapなDelayを、feedforwardを3 tap と feedbackを3 tap 持たせまして、
前回( Web Audio API で、内蔵マイクで録音、ただしFirefox - shingoushori's dialy )
... のやつに繋いでみました。
内蔵マイクにDelay, wavを2つ同時再生してそちらにもDelay、ただしFirefox

 

実装してみて気づいたのが、3 tapのfeedbackのゲイン係数の発振条件。
1本だけなら、絶対値を1未満にしておけばいいわけです。
今回は3 tapが並列になるわけで、
遅延量が整数比の時には、倍数の経路でのゲイン係数が、
実際には約数の経路のゲイン係数との和になるわけですな。
条件を計算するのは後回しとしまして、
今回はとりあえず絶対値を0.33以下にしておきました。

Canvasで、はてなブログに回路図を直接描いてみるテスト(Diode Clipping)

HTML5 JavaScript Canvas エフェクタ / Stompbox 電子回路 / Electronic Circuit

はてなブログにできるだけ写真を投稿したくない!容量が気になるから.
でも、図やグラフを貼り付けたい!わかりやすいし、格好いいから.
この相反する気持ちの矛先として、Canvasに目をつけたわけです.

とりあえず最近のマイブーム、Diode clipperを描いてみました.

CanvasJavaScriptで関数化できるので、
巧くやればSVGファイルを頑張って貼るより色々楽しい予感がします.
Canvas要素の英語版wikiには、SVGとの比較が言及されていますな.

Web Audio API で、内蔵マイクで録音、ただしFirefox

HTML5 JavaScript Web Audio API 信号処理 / Signal Processing

前回、Web Audio API で、WAVファイルに書き出ししました.
今度はマイクの入力に手を出してみました.
ただし、録音はwavファイルの再生中のみで、
出力はwavファイルとの加算結果です.
さらに、どうにもFirefoxだけでしか動かない.

Google Chromeで動かないのが苦しいところ.
探してみると2013年あたりの文献が多く、しかもなにやら設定を変更せよとのこと.
http://www.html5rocks.com/ja/tutorials/getusermedia/intro/
http://slowquery.hatenablog.com/entry/2013/02/20/020321
https://developers.google.com/web/updates/2012/09/Live-Web-Audio-Input-Enabled
しかし、2016年3月現在の私のChromeでは記載の設定は見当たりませんでした.

Google Chromeで動くものもあり、
Simple microphone Web Audio API / WebRTC example – Nic Does Code
Pitch Detector
動かないものもあり...その違いが今の所わかりません.

Web Audio API で、WAVファイルに書き出してみる、再生終了後にダウンロード

HTML5 JavaScript Web Audio API 信号処理 / Signal Processing

これまでちまちまとWeb Audio APIで実装を試みてきました.
このあたりでWAVファイルへの書き出しに手を出してみました.

今回は、2つのファイルを同時再生し、
2つとも再生終了後に同時再生の結果をWAVファイルに書き出します.

書き出し可能になった時点で、"ダウンロード"にリンクが発生します.

怪しかったところが、再生終了のタイミングです.
onendedのタイミングで再生終了とすると、尻切れになってしまいました.
今回は乱暴に、onendedのタイミングからsetTimeoutによって遅らせました.

↓頼りきりになってしまった引用文献↓
http://qiita.com/HirokiTanaka/items/56f80844f9a32020ee3b
http://www.cyokodog.net/blog/media-capture-and-streams-web-audio-api/

Web Audio API で、the sliding Goertzel DFT filter のパラメータを弄ってみる、とりあえずNaN

HTML5 JavaScript Web Audio API エフェクタ / Stompbox 信号処理 / Signal Processing

前回、Web Audio API でthe sliding Goertzel DFT filterを実装し、
パラメータをいじりました.
しかし、入力された文字列によっては発散する恐れがありました.

今回は、入力された文字列に関門を設け、
想定外の数値となる場合は反映しないようにしました.

そこで一癖あったのが、NaNでした.
参考にしたページがこちら→NaNの判定について
JavaScriptの関数の癖だけでなく、主観的なNaNとプログラム上でのNaNは違うわけです.
数字でなくも文字列は、文字コードでもってNumberであり、NaNではない.
賢い関数がありそうなものですが、とりあえず単純に組んでみました.

Web Audio API で、the sliding Goertzel DFT filter のパラメータを弄ってみる、とりあえず

HTML5 JavaScript Web Audio API エフェクタ / Stompbox 信号処理 / Signal Processing

↓前回、the sliding Goertzel DFT filterを組みました. ↓
Web Audio API で、the sliding Goertzel DFT filter を試作 (1帯域) - shingoushori's dialy

今回は、パラメータを弄ってみました. とりあえず、です.
とりあえずポイント1: inputフォームを使う
とりあえずポイント2: 数値および数値の変更手順によっては、発散する
"ぷちっ"とノイズが出て、以後可聴な音が出なくなるわけです.
危険です. パラメータ変更に関しては、安全策を考える必要が有ります.
このサンプルをお使いになられてのトラブルについては、一切の責任を負いかねます...

 


fが中心周波数,rがdamping factor.
rについては,1以上の数値を入れると発散します.入れないでください!
fについては,DFTであるからk=f/(Fs/NDFT)が整数であるべきです.
ここで,k:周波数ビン番号,Fs:サンプリング周波数, NDFT:DFT点数です.
従って,k=round(f/(Fs/NDFT))とでもして整数化する実装が普通でしょう.
ところが,roundせずともフィルタリング自体はできているようです.
興味深い...

Web Audio API で、the sliding Goertzel DFT filter を試作 (1帯域)

HTML5 JavaScript Web Audio API エフェクタ / Stompbox 信号処理 / Signal Processing 文献 / bibliography

Web Audio APIでのSTFTによる帯域分割がうまくいかないので,
the sliding Goertzel DFT filterに抜け道を求めました.

↓the sliding Goertzel DFT filterの素敵な文献↓
The Sliding DFT
SLIDING IS SMOOTHER THAN JUMPING

DFTの1帯域分に着目すれば,IIRフィルタで実装できるわけです.
しかも, フィルタだから毎サンプルでの算出結果が得られる.

 

とりあえず, DFT点数を1024, 着目する周波数ビン番号を20としてみました.
ただし, 負の周波数ビンとカップリングし,虚数が出ないようにしています.
さらに,発散しないように damping factor : r = 0.995で, 極を単位円から離しました.
数値は耳で聞いて設定しました.
damping factorがあるのでDFTと完全に一緒でもない.

 

今回, IIRフィルタをScriptProcessorNodeで組みました.
Web Audio APIにはIIRFilterNodeもありそうですが,私の環境では見つかりませんでした.
ScriptProcessorNodeも廃止が告知されており,
AudioWorkerNodeに置き換えられるそうで.
しかし,AudioWorkerNodeも私の環境にはまだ無い.
儚いものです...

 

最後に,ScriptProcessorNodeに引数とバッファを持たせる方法について.
JavaScriptでは, こんな感じにほいほい追加できる↓
オブジェクトを利用する
気づくまでに時間がかかり,
チャネル数を偽装して引数を渡そうとするなど,悪戦苦闘しました.