Created
November 22, 2021 01:59
-
-
Save tatmos/e8ac522c4e311091c1fcbba1f4f8edca to your computer and use it in GitHub Desktop.
toioとKOOVで生楽器のtoio部分の制御processingファイル(MIDI入力、顔位置からMIDI出力とtoio制御)
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import processing.video.*; | |
import gab.opencv.*; | |
import java.awt.Rectangle; | |
Capture video; | |
OpenCV opencv; | |
Rectangle[] faces; | |
import themidibus.*; | |
MidiBus myBus; | |
ArrayList<Cube> cubes = new ArrayList<Cube>(); | |
Cube cube_sel = null; | |
boolean keyDown = false; | |
void setup() { | |
size(640, 680); | |
int N = 2; // 接続するキューブの個数 | |
// キューブの接続は1つずつ行う。 | |
// 同時に行うと同じものに接続してしまうことがあるので、 | |
// 作成したインスタンスが connected になるまで待つ。 | |
while ( cubes.size() < N ) { | |
Cube c = new Cube(this); | |
print( "cube " + cubes.size() + " is trying to connect."); | |
while ( !c.connected ) { | |
print("."); | |
delay(100); | |
} | |
println("\ncube " + cubes.size() + " is connected!"); | |
cubes.add(c); | |
} | |
// 0番目のキューブを操作対象にする | |
cube_sel = cubes.get(0); | |
// 起動時にウィンドウをアクティブにするための命令 | |
((java.awt.Canvas)surface.getNative()).requestFocus(); | |
video = new Capture(this, 640, 480, 30); | |
video.start(); | |
//OpenCVSetup(); | |
MIDISetup(); | |
} | |
void MIDISetup() | |
{ | |
//MIDIデバイスのリストを表示 | |
MidiBus.list(); | |
myBus = new MidiBus(this, "KOMPLETE KONTROL M32 MIDI", "MocoLUFA"); | |
} | |
int[] backCount = {0,0}; | |
int speed = 100; | |
int centerPos = 247; | |
int paperwidth = 30; | |
int interWidth = 5; | |
int paperYOffset = -25; | |
void draw() { | |
background(50); | |
fill(255); | |
textSize(25); | |
OpenCVTask(); | |
// 各キューブの位置・角度の表示 | |
for (int i=0; i<cubes.size(); i++) { | |
Cube cube = cubes.get(i); | |
text("cube " + i, 20, 40 ); | |
text("x=" + cube.x, 40, 80 ); | |
text("y=" + cube.y, 40, 120 ); | |
text("angle=" + cube.angle, 40, 160 ); | |
translate(0, 200); | |
//// Area外は止まる | |
//if(!checkArea(cube,paperwidth)){ | |
// backCount[i] = 5; | |
//} | |
//// バックが必要なら | |
//if(backCount[i] > 0) | |
//{ | |
// if(checkArea(cube,interWidth)){ | |
// backCount[i] = 0; | |
// } | |
// backCount[i]--; | |
// cube.moveTo(centerPos, centerPos, speed); | |
//} | |
} | |
} | |
// エリア外だとfalse | |
Boolean checkArea(Cube cube,int rlength) | |
{ | |
if(cube.x > centerPos + rlength) return false; | |
if(cube.x < centerPos - rlength) return false; | |
if(cube.y > centerPos-paperYOffset + rlength) return false; | |
if(cube.y < centerPos-paperYOffset - rlength) return false; | |
return true; | |
} | |
void keyPressed() { | |
// キーリピートを防ぐ仕組み | |
if ( keyDown ) return; | |
keyDown = true; | |
// 操作するキューブの選択 | |
if ( key == '1' ) cube_sel = cubes.get(0); | |
if ( key == '2' ) cube_sel = cubes.get(1); | |
if ( keyCode == UP ) cube_sel.move(speed, speed); // 移動。左右輪の移動速度を指定 | |
if ( keyCode == DOWN ) cube_sel.move(-speed, -speed); | |
if ( keyCode == LEFT ) cube_sel.move(-speed, speed); | |
if ( keyCode == RIGHT ) cube_sel.move(speed, -speed); | |
if ( key == 'g' ) cube_sel.moveTo(centerPos, centerPos, speed); // 目標位置へ移動 (x,y,移動速度) | |
if ( key == 's' ) { | |
cube_sel.playSound(1, 100); // サウンド再生 (サウンドID, 音量) | |
MoveCube(cubes.get(0),-20,20,speed); | |
MoveCube(cubes.get(1),20,20,speed); | |
} | |
// 全力バック | |
if ( key == 'z' ) | |
{ | |
cubes.get(0).move(-speed, -speed); | |
cubes.get(1).move(-speed, -speed); | |
} | |
// 停止 | |
if ( key == 'q' ) | |
{ | |
cubes.get(0).move(-0, -0); | |
cubes.get(1).move(-0, -0); | |
} | |
if ( key == 'a' ) | |
{ | |
MoveCube(cubes.get(0),-paperwidth,-paperwidth,speed); | |
MoveCube(cubes.get(1),paperwidth,paperwidth,speed); | |
} | |
if ( key == 'b' ) | |
{ | |
MoveCube(cubes.get(0),-paperwidth,paperwidth,speed); | |
MoveCube(cubes.get(1),paperwidth,-paperwidth,speed); | |
} | |
if ( key == 'c' ) | |
{ | |
MoveCube(cubes.get(0),paperwidth,paperwidth,speed); | |
MoveCube(cubes.get(1),-paperwidth,-paperwidth,speed); | |
} | |
if ( key == 'd' ) | |
{ | |
MoveCube(cubes.get(0),paperwidth,-paperwidth,speed); | |
MoveCube(cubes.get(1),-paperwidth,paperwidth,speed); | |
} | |
} | |
// キーを離したら停止 | |
void keyReleased() { | |
keyDown = false; | |
} | |
void controllerChange(int channel, int number, int value){ | |
float x,y; | |
if(number == 1){ | |
x = map(value,0,127,0,width); | |
}else{ | |
y = map(value,0,127,0,width); | |
} | |
//動かしたコントロールの値を表示 | |
println("channel:" + channel + " number:" + number +" value:"+ value); | |
// cube_sel.move(63+value, 63-value); | |
} | |
void noteOff(int channel, | |
int pitch, | |
int velocity){ | |
keyDown = false; | |
} | |
void noteOn(int channel, | |
int pitch, | |
int velocity){ | |
myBus.sendNoteOn(channel, pitch+36, velocity); // Send a Midi noteOn | |
delay(200); | |
myBus.sendNoteOff(channel, pitch+36, velocity); // Send a Midi nodeOff | |
println("channel:" + channel + " pitch:" + pitch +" velocity:"+ velocity); | |
if ( keyDown ) return; | |
keyDown = true; | |
toggleStartCount++; | |
if ( pitch == 48 ) | |
{ | |
MoveCube3(cubes.get(0),-paperwidth,-paperwidth,speed,180+45); | |
MoveCube2(cubes.get(1),paperwidth,paperwidth,speed); | |
return; | |
} | |
if ( pitch == 50 ) | |
{ | |
MoveCube2(cubes.get(0),-paperwidth,paperwidth,speed); | |
MoveCube2(cubes.get(1),paperwidth,-paperwidth,speed); | |
return; | |
} | |
if ( pitch == 52 ) | |
{ | |
MoveCube2(cubes.get(0),paperwidth,paperwidth,speed); | |
MoveCube3(cubes.get(1),-paperwidth,-paperwidth,speed,180+45); | |
return; | |
} | |
if ( pitch == 53 ) | |
{ | |
MoveCube2(cubes.get(0),paperwidth,-paperwidth,speed); | |
MoveCube2(cubes.get(1),-paperwidth,paperwidth,speed); | |
return; | |
} | |
if(toggleStartCount % 2 == 0){ | |
// 上のキー以外なら | |
MoveCube(cubes.get(0),-40,20,speed); | |
MoveCube(cubes.get(1),40,20,speed); | |
} else { | |
MoveCube(cubes.get(0),-40,-20,speed); | |
MoveCube(cubes.get(1),40,-20,speed); | |
} | |
} | |
int toggleStartCount = 0; | |
void OpenCVSetup() | |
{ | |
if (video.available()) video.read(); | |
} | |
boolean headOn = false; | |
boolean openCvFinish = false; | |
void OpenCVTask() | |
{ | |
if (video.available()){ | |
video.read(); | |
} else { | |
return; | |
} | |
if(openCvFinish == false) | |
{ | |
openCvFinish = true; | |
opencv = new OpenCV(this, video); | |
opencv.loadCascade(OpenCV.CASCADE_FRONTALFACE); | |
} | |
opencv.loadImage(video); //ビデオ画像をメモリに展 | |
faces = opencv.detect(); | |
// caputure画像表示 | |
image(opencv.getInput(), 0, 0); | |
for (int i = 0; i < faces.length; i++) { | |
//image(pic, faces[i].x, faces[i].y, faces[i].width, faces[i].width); | |
//(貼り付ける画像、x座標、y座標、横の長さ、縦の長さ) | |
//画像の表示位置は微調整してください | |
circle(faces[i].x, faces[i].y, 50); | |
if(faces[i].x < 200) | |
{ | |
headOn = false; | |
} | |
if(headOn) return; | |
headOn = true; | |
if(faces[i].x < 200) | |
{ | |
fill(50); | |
circle(faces[i].x, faces[i].y, 50); | |
myBus.sendNoteOn(0, 7+48+36, 127); // Send a Midi noteOn | |
delay(100); | |
myBus.sendNoteOff(0, 7+48+36, 127); // Send a Midi nodeOff | |
toggleStartCount++; | |
if(toggleStartCount % 2 == 0){ | |
// 上のキー以外なら | |
MoveCube(cubes.get(0),-40,20,speed); | |
MoveCube(cubes.get(1),40,20,speed); | |
} else { | |
MoveCube(cubes.get(0),-40,-20,speed); | |
MoveCube(cubes.get(1),40,-20,speed); | |
} | |
} | |
} | |
} | |
void MoveCube(Cube cube,int x,int y,int speed) | |
{ | |
cube.moveTo(centerPos+x, centerPos+y+paperYOffset, speed); | |
} | |
void MoveCube2(Cube cube,int x,int y,int speed) | |
{ | |
MoveCube3(cube,x,y,speed,180); | |
} | |
void MoveCube3(Cube cube,int x,int y,int speed, int angle) | |
{ | |
cube.moveTo(centerPos+x, centerPos+y+paperYOffset, speed, angle, (byte)0x01,(byte)0x00,(byte)0); | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment