p5jsトップに戻る    印刷する

音に反応する

コンピュータに内蔵の、あるいは接続されたマイクから音を入力し、それに応答するようなプログラムを作ります。p5.jsが提供するp5.soundライブラリを使います。
Processingのメニュー[スケッチ][ライブラリをインポート] でp5.soundを選択すると、ライブラリがスケッチフォルダのlibraryフォルダ内に取り込まれ、スケッチを保存すると、index.html内に次のscriptタグが追加されます。
<script language="javascript" type="text/javascript" src="libraries/p5.sound.min.js"> </script>

マイクからの音の大きさに応答

マイクからの入力音に応じて、描く円の大きさが変化するスケッチが、リスト6_1です。

音声入力を処理するオブジェクトp5.AudioInを使います。 マイクからの入力を処理するいわばプログラムの部品で、実際に働くオブジェクトを作って、スケッチの中で使います。JavaScriptのオブジェクトに関しては、このページで説明しています。

p5.AudioInオブジェクトを作るには new演算子を使います。 次のように、p5.AudioInオブジェクトを作り、マイクから音を入力し、グラフィックスに反映させます。
【リスト6-1】
var mic;  //AudioInオブジェクト用変数←(1)
function setup() {
  createCanvas(250, 250);
  mic = new p5.AudioIn();   //AudioInの生成←(2)
  mic.start();              //AudioIn機能を開始←(3)
  fill(200, 0, 0);
}

function draw() {
  background(0);
  var vol = mic.getLevel(); //音量を取得←(4)
  //↓(5) 入力値(0から1)を0から500に換算
  var d = map(vol, 0, 1, 0, width*2); 
  ellipse(width/2, width/2, d, d); //描画
}


マイク入力のノイズ除去とイージング効果

リスト6_1は、マイクからの入力を0~500の間の値に換算し、それを円の直径としていました。これだと、入力のノイズもそのまま円の大きさに反映するため、動きが細かく変化します。 そこで、今の値と、次の入力値の差が一定以上の場合だけ、円の大きさを変えるようにします。
加えて、音の変化を直接そのまま円の大きさの変化とせず、徐々にその大きさに近づいていくように、 イージング効果を付けます。リスト6_1より、スムーズに変化することを、実際に確かめてください。
【リスト6-2】
var mic;  //AudioInオブジェクト用変数←(1)
var easing = 0.1; //イージングの係数
var adjD = 0;     //イージングで調整した円の直径
function setup() {
  createCanvas(250, 250);
  mic = new p5.AudioIn();//AudioInの生成←(2)
  mic.start();           //AudioIn機能を開始←(3)
  fill(200, 0, 0);
}

function draw() {
  background(0);
  var vol = mic.getLevel();    //音量を取得←(4)
  var d = map(vol, 0, 1, 0, width*2); //入力値(0から1)を0から500に換算←(5)
  var sa = d - adjD;           //入力値から直接計算した値と今の直径との差 
  if (abs(sa) > 1) {           //差の絶対値が1より大きい時だけ直径を変える
    adjD = adjD + sa * easing; //差の0.1分ずつ変化
  }
  ellipse(width/2, width/2, adjD, adjD); //描画
}

音声ファイルの再生と応答

リスト6_1は、マイクから入力した音量に応答するスケッチでした。これを音声ファイルの音に応じて、円の大きさが変わるようにします。

音声ファイルへのアクセスは、p5.SoundFileオブジェクトを使って行います。音声ファイルへのパスを指定して、p5.SoundFileオブジェクトを生成しておき、p5.SoundFileオブジェクトのメソッドにより、音声を再生、停止します。

音の大きさは、振幅(amplitude)と関係しています。p5 soundライブラリのp5.Amplitudeオブジェクトを使って、値を得ます。
電気信号の世界では、値(実効値)を、一定の時間区間の信号の平均的な大きさとして表します。「平均的な大きさ」とは、測定した値の二乗平均平方根(Root Mean Square:二乗した値の平均値の平方根、RMS値)です。 p5.AmplitudeオブジェクトのgetLevel()メソッドは、1024回データを読み、そのRMS値を計算します(0?1.0の値)。

次のように、音声ファイルをロードし、その振幅を、グラフィックスに反映させます。

クリックで音声を再生、停止
【リスト6-3】
var song, analyzer;  //p5.SoundFileとp5.Amplitude用の変数を定義←(1)

function preload() { //音声ファイルをロードしておく←(2)
  song = loadSound('data/funaJingle.mp3');
} 

function setup() {
  createCanvas(250, 250);
  fill(200, 0, 0);
  analyzer = new p5.Amplitude();//Amplitudeの生成←(3)
  analyzer.setInput(song);//Amplitudeからの入力開始←(4)
}

function draw() {
  background(0);
  var rms = analyzer.getLevel();      // 振幅の平均値を取得 (0から1.0の間の値)←(5)
  var d = map(rms, 0, 1, 0, width*2); //入力値(0から1)を0から500に換算←(6)
  ellipse(width/2, width/2, d, d);    //描画
}

function mousePressed() {             //マウスクリックで音声を再生、停止←(7)
  if (song.isPlaying()){
    song.stop();
  } else {
    song.loop();
  }
}

演習問題


【問題12-1】写真を複数枚用意し、マイクが感知した音の大きさに応じて、表示される写真が変化するプログラムを作ってください。
左図は、9枚の猫のあくびの連続写真を用意し、マイクからの音が大きい時は口を大きく開けた写真を、音が小さい時は口を閉じた写真を表示するようにしています。 入力値が一定以上の時は、最後2枚の写真を交互に表示し、大あくびをしているような効果をつけました。
声を出していっしょにあくびをするような感覚を楽しめるでしょうか。

左図で使っている画像(9枚の猫のあくび写真)をcatフォルダにまとめた圧縮ファイルcat.zipを用意しました。リンクをマウスで右クリックし、メニューから[対象をファイルに保存]。

この写真を使って、あるいは、自分が用意した別の写真やイラストを使って、音と画像が関連するおもしろい内容のコンテンツを考えてみてください。

一つの例を次に載せます。 Happy Birthday

arigat アットマーク acm.org / copyright © info