Interactive Music II ProcessingとSuperColliderの連携1

3,656 views

Published on

Published in: Business, Technology
0 Comments
2 Likes
Statistics
Notes
  • Be the first to comment

No Downloads
Views
Total views
3,656
On SlideShare
0
From Embeds
0
Number of Embeds
1,085
Actions
Shares
0
Downloads
43
Comments
0
Likes
2
Embeds 0
No embeds

No notes for slide

Interactive Music II ProcessingとSuperColliderの連携1

  1. 1. Interactive Music II ProcessingとSuperColliderの連携1 東京藝術大学芸術情報センター (AMC) 2014年1月8日 田所 淳
  2. 2. 今日の内容 ‣ いよいよ、Processingと、SuperColliderの連携に挑戦!!
  3. 3. 今日の内容 ‣ ProcessingとSuperColliderの連携をするには、Processingにラ イブラリ(Library)を追加する ! ‣ OSCのためのライブラリ ‣ oscP5を使用 ! ‣ SuperColliderとの連携に特化したライブラリ ‣ SuperCollider Client for Processing
  4. 4. oscP5 ‣ まずは、oscP5をインストールする ‣ メニューから、Sketch > Import Library > Add Library を選択
  5. 5. oscP5 ‣ Library Manager のウィンドウが表示される ‣ 検索欄に「oscP5」と入力 ‣ 表示された、oscP5の横の「Install」ボタンを押す
  6. 6. oscP5 ‣ 早速、OSCを使用して、ProcessingからSuperColliderにメッセー ジを送ってみる ! ‣ SuperCollider側: OSCメッセージのDumpを設定 ! s.dumpOSC; ! ! ‣ 次に、メッセージを送出するProcessingのテストプログラムを 作成する
  7. 7. oscP5 ‣ Processing側: OSCメッセージ送出プログラム //OSCのライブラリ読み込み import oscP5.*; import netP5.*; ! //OSC送受信のオブジェクト OscP5 oscP5; //送出先のネットアドレス NetAddress remote; ! void setup() { //画面基本設定 size(400,400); frameRate(60); //OSC送受信のオブジェクトを生成 oscP5 = new OscP5(this, 12000); //ネットアドレスを設定 remote = new NetAddress("127.0.0.1", 57110); }
  8. 8. oscP5 ‣ Processing側: OSCメッセージ送出プログラム void draw() { background(0); } ! //マウスクリックに反応 void mouseReleased() { //OSCメッセージを生成 OscMessage msg = new OscMessage("/test"); //引数を追加 msg.add(123); msg.add("Hello"); //OSC送出 oscP5.send(msg, remote); }
  9. 9. oscP5 ‣ Processingを実行すると、SuperColliderのPost Windowに以 下のようなメッセージが出現するはず ! [ "/test", 123, "Hello" ] ! FAILURE IN SERVER: /test Command not found ! ! ‣ Processingで生成したOSCメッセージを受信している ‣ ただし、SuperCollider側はまだ何もしていないのでエラーを 表示
  10. 10. oscP5 ‣ 次に、SuperColliderで楽器(Synth)を定義して、それを Processingから演奏してみる
  11. 11. oscP5 ‣ SuperCollider側: 「test_inst」を定義 SynthDef("test_inst",{ arg freq=440, length=1.0, amp=0.5; var env, out; env = Env.perc(0.01, length); out = SinOsc.ar([freq,freq*1.001]) * EnvGen.kr(env, doneAction:2) * amp; Out.ar(0, out); }).store;
  12. 12. oscP5 ‣ Processing側: //OSCのライブラリ読み込み import oscP5.*; import netP5.*; ! //OSC送受信のオブジェクト OscP5 oscP5; //送出先のネットアドレス NetAddress remote; //カウンター int counter; ! void setup() { //画面基本設定 size(400,400); frameRate(60); //OSC送受信のオブジェクトを生成 oscP5 = new OscP5(this, 12000); //ネットアドレスを設定 remote = new NetAddress("127.0.0.1", 57110); }
  13. 13. oscP5 ‣ Processing側: void draw() { background(0); } ! //マウスクリックに反応 void mouseReleased() { //OSCメッセージを生成 OscMessage msg = new OscMessage("/s_new"); //SuperColliderのパラメータを設定 msg.add("test_inst"); //Synth名 msg.add(1000 + counter); //Synth ID msg.add(1); //アクションNo. msg.add(0); //ノードID //OSC送出 oscP5.send(msg, remote); counter++; }
  14. 14. oscP5 ‣ 画面をクリックすると、音が鳴る(はず)
  15. 15. oscP5 ‣ マウスのクリックする高さ(Y座標)で、音程が変化するように改 造してみる!
  16. 16. oscP5 ‣ Processing側: mouseReleased() 関数を変更 //マウスクリックに反応 void mouseReleased() { //OSCメッセージを生成 OscMessage msg = new OscMessage("/s_new"); //SuperColliderのパラメータを設定 msg.add("test_inst"); //Synth名 msg.add(1000 + counter); //Synth ID msg.add(1); //アクションNo. msg.add(0); //ノードID //マウスのy座標で、音程を変更する msg.add("freq"); msg.add(map(mouseY, height, 0, 20, 8000)); //OSC送出 oscP5.send(msg, remote); counter++; }
  17. 17. SuperCollider client for Processing ‣ SuperCollider client for Processing ‣ OSCp5よりも簡単に、SuperColliderとProcessingの連携が可 能となる ‣ こちらをより積極的に活用していきたい!
  18. 18. SuperCollider client for Processing ‣ インストール ‣ oscP5と同様に、Library Managerからインストール
  19. 19. SuperCollider client for Processing ‣ Processing側: こんなに簡単に! import supercollider.*; import oscP5.*; ! Synth synth; ! void setup () { size(600, 400); } ! void draw() { background(0); } ! //マウスクリックに反応 void mouseReleased() { //新規に楽器を定義(まだ生成はされず) synth = new Synth("test_inst"); //引数を設定 synth.set("amp", 0.5); synth.set("freq", map(mouseY, height, 0, 20, 8000)); //楽器を生成 synth.create(); }
  20. 20. SuperCollider client for Processing ‣ Processing側にアニメーションをつけてみる ! ‣ 例えば… ‣ マウスをクリックすると、円が波紋のように拡がる
  21. 21. SuperCollider client for Processing ‣ Processing側: import supercollider.*; import oscP5.*; ! Synth synth; int NUM = 100; float[] radius = new float[NUM]; PVector[] pos = new PVector[NUM]; int counter = 0; ! void setup () { size(800, 600); frameRate(60); noFill(); stroke(31, 127, 255); strokeWeight(3); for (int i = 0; i < NUM; i++) { radius[i] = 0; pos[i] = new PVector(width*2, width*2); } }
  22. 22. SuperCollider client for Processing ‣ Processing側: void draw() { background(0); for (int i = 0; i < NUM; i++) { ellipse(pos[i].x, pos[i].y, radius[i], radius[i]); radius[i] += 1; if(radius[i] > width*1.5){ radius[i] = 0; pos[i].x = width*2; pos[i].y = width*2; } } } ! void mouseReleased() { synth = new Synth("test_inst"); synth.set("amp", 0.5); synth.set("freq", map(mouseY, height, 0, 20, 8000)); synth.create(); int n = counter % NUM; radius[n] = 0; pos[n].x = mouseX; pos[n].y = mouseY; counter++; }
  23. 23. SuperCollider client for Processing ‣ 完成!!
  24. 24. SuperCollider client for Processing ‣ 応用: ‣ 先週のアニメーションのサンプルを応用 ‣ 壁にぶつかったとき、音が鳴る
  25. 25. たくさんの図形を同時に動かす ‣ Processing: 先週のサンプル int NUM = 500; //配列の数 //位置のベクトルの配列 PVector[] location = new PVector[NUM]; //速度のベクトルの配列 PVector[] velocity = new PVector[NUM]; //塗りの色の配列 color[] col = new color[NUM]; //円の大きさ(直径)の配列 float[] diameter = new float[NUM]; ! void setup() { size(640, 480); //640x480pixelの画面を生成 frameRate(60); //フレームレート noStroke(); for (int i = 0; i < NUM; i++) { //配列の数だけ繰り返し //位置のベクトルの初期設定 location[i] = new PVector(random(width), random(height)); //速度のベクトルの初期設定 velocity[i] = new PVector(random(-4, 4), random(-4, 4)); //色の初期設定 col[i] = color(random(255), random(255), random(255), 127); //大きさの初期設定 diameter[i] = random(3, 40); } }
  26. 26. たくさんの図形を同時に動かす ‣ Processing: 先週のサンプル void draw() { background(15); //背景を描画 //配列の数だけ繰り返し for (int i = 0; i < NUM; i++) { fill(col[i]); //色を指定 //指定した位置に円を描画 ellipse(location[i].x, location[i].y, diameter[i], diameter[i]); //位置のベクトルに速度のベクトルを加算、次の位置になる location[i].add(velocity[i]); //もし画面の左端、または右端に到達したら if ((location[i].x > width) || (location[i].x < 0)) { velocity[i].x *= -1; //X方向のスピードを反転 } //もし画面の下端、または上端に到達したら if ((location[i].y > height) || (location[i].y < 0)) { velocity[i].y *= -1; //Y方向のスピードを反転 } } }
  27. 27. SuperCollider client for Processing ‣ このプログラムを改造する ! ‣ draw() 関数内 ‣ if文で壁にあたった瞬間を検知している部分で、楽器を生成し、 演奏する ! ‣ プログラムを読み易くするため、新規に「playSynth()」 関数 を作成 ‣ void playSynth(x座標、y座標)
  28. 28. たくさんの図形を同時に動かす ‣ Processing: draw()関数にplaySynth()を追加 void draw() { background(15); //背景を描画 //配列の数だけ繰り返し for (int i = 0; i < NUM; i++) { fill(col[i]); //色を指定 //指定した位置に円を描画 ellipse(location[i].x, location[i].y, diameter[i], diameter[i]); //位置のベクトルに速度のベクトルを加算、次の位置になる location[i].add(velocity[i]); //もし画面の左端、または右端に到達したら if ((location[i].x > width) || (location[i].x < 0)) { velocity[i].x *= -1; //X方向のスピードを反転 playSynth(location[i].x, location[i].y); } //もし画面の下端、または上端に到達したら if ((location[i].y > height) || (location[i].y < 0)) { velocity[i].y *= -1; //Y方向のスピードを反転 playSynth(location[i].x, location[i].y); } } }
  29. 29. たくさんの図形を同時に動かす ‣ Processing: playSynth関数 void playSynth(float x, float y) { //新規に楽器を定義(まだ生成はされず) Synth synth = new Synth("test_inst"); //引数を設定 synth.set("amp", 0.5); synth.set("freq", map(x, height, 0, 20, 8000)); //楽器を生成 synth.create(); }
  30. 30. SuperCollider client for Processing ‣ 完成!! ‣ 円のバウンドにあわせて、音が鳴るはず!

×