시각화/프로세싱

▶Processing :: 프로세싱 기초예제 – video #3 움직임 감지하기

비주얼라이즈 2014. 5. 29. 15:16


Processing :: 프로세싱 기초예제 – video #3

움직임을 감지하고 추적하기



이번 포스팅에서는 지난 #1, #2예제와 마찬가지로

video를 불러온다음 이것을 이용하여 여러가지 조작을 해보는 과정으로

'움직임을 감지하고 추적하기'에 대해서 살펴보고자합니다.








import processing.video.*;

Capture cam;
PImage preFrame;
float threshold = 50;


사전 설정을 해주는 부분입니다.


preFrame부분이 이전 프레임을 저장할 변수입니다.

그리고 그아래에있는 threshold는 옵션 값인데요

'얼마나 다른 픽셀을 움직인 것이라고 판단할 지'에 대해서 설정하는 부분입니다.



void setup(){
  size(640, 480);
  smooth();
 
  String[] cameras = Capture.list();
 
  cam = new Capture(this, width, height, 30);
  preFrame = createImage(cam.width, cam.height, RGB);
 
  cam.start();
}



지난 기초예제 #1, #2의 setup()부분과 다른 부분을 발견하셨나요?

이번 예제에서 다르게 세팅되는 부분은

'preFrame'부분입니다.

여기에서 비디오와 같은 크기를 가진 이미지를 만들 수 있도록 세팅 해놓습니다.



void draw(){
 
  if(cam.available() == true){
   
    preFrame.copy(cam, 0, 0, cam.width, cam.height, 0, 0, cam.width, cam.height);
    preFrame.updatePixels();
   
    cam.read();
  }

 


역시 이전 예제와 마찬가지로 

available()함수를 이용하여 camera의 이미지 존재여부를 판단하여

camera.read()함수로 이미지 정보를 불러오게 되는데요~


그리고 그 사이에있는 preFrame.copy()를 확인하셨나요?

이번 예제가 '움직임 감지하기'인 만큼

이번에는 특별히 출력물에 '움직임'을 표현해야하겠지요~


그렇다면 움직임을 만들어내는걸까요?

당연히 아니겠지요!


감지하기 = 직전 움직임을 기억하고, 출력하기

즉, 이전 프레임의 정보를 저장한 뒤 출력해주는 방법으로

'움직임 감지하기'를 표현하게 되는 것입니다.



 loadPixels();
  cam.loadPixels();
  preFrame.loadPixels();

 

여기에서 cam과 preFreame의 픽셀정보를 불러오게됩니다.

loadPixels()함수는 PImage부분을 공부할 때 사용했었는데요~

PImage에 적용했던 크기, 색조, 움직임등의 기능은 

Capture객체에도 적용할 수 있습니다.^^



 
  for(int x = 0; x < cam.width; x++){
    for(int y = 0; y < cam.height; y++){


이 부분이 '모든 픽셀을 훑어라!'라는 명령을 내리는 부분입니다.

x는  0부터 시작해서 cam의 width값까지 진행하고

y는 0부터 시작해서 cam의 height값까지 진행합니다.



      int loc = x + y * cam.width;
     
      color current = cam.pixels[loc];
      color previous = preFrame.pixels[loc];
     


<int loc = x + y * cam.width;> 이 부분은 자주 보게되는데요

픽셀의 1차원 좌표를 나타냅니다.


이어지는 current의 부분에서 '현재의 색'을 잡아내게되고

previous을 통해  '이전의 색'을 나타내게 되는 구조입니다.



      float r1 = red(current); float g1 = green(current); float b1 = blue(current);
      float r2 = red(previous); float g2 = green(previous); float b2 = blue(previous);
     
      float diff = dist(r1, g1, b1, r2, g2, b2);
     


상단의 두 줄은 current와 previous의 RGB값을 각각 나타내며

하단의 'diff'에서 dist()함수를 이용하여

 두 색상 값을 비교할 수 있는 옵션을 만들어줍니다.



      if(diff > threshold){
        pixels[loc] = color(0);
      } else {
        pixels[loc] = color(255);
      }
    }
  }
  updatePixels();
}
}

이제 마지막 부분입니다.


if()를 이용하여 current와 preFrame의 색상차이가

 얼마나 나는지 분석하게되는데요


이번 예제 시작할 때 설정해두었던 'threshold'값을 기준으로

두 색상값의 차이가 threshold값보다 크면 검은색(color(0))을 주고,

두 색상값의 차이가 threshold값보다 작다면 흰색(color(255))를 주는 방식입니다.






우리가 앞서 threshold값을 이야기할 때

'얼마나 다른 픽셀을 움직인 것이라고 판단할 지'에 대해서 설정하는 부분이라고 했었는데요


프로세싱이 이 값을 기준으로 '움직임의 여부'를 판단할 수 있도록 해주는 것입니다.


마지막으로 updatePixels()를 입력해주는 것을 잊지마세요^^


loadPixels()는 픽셀배열에 접근하기 전에 입력해주는 함수

updatePixels()는 우리가 픽셀사용을 다 했을때 프로세싱에게 '끝났음'을 알려주는 함수









[프로세싱 기초예제 video - 움직임 추적하기]