시각화/프로세싱

▶함께배우는 프로세싱 :: generative design P.2.2.3 Shape from agents

비주얼라이즈 2015. 2. 3. 15:55



▶함께배우는 프로세싱 :: generative design P.2.2.3 Shape from agents


이번 글에서는 generative design에서 제공하고있는 예제를 살펴보려고합니다. 






마우스를 클릭하면 그 지점을 기준으로 새롭게 agent들의 위치가 설정됩니다. (클릭위치에 도형생성) 이렇게 설정된 위치에 curveVertex()로 꼭짓점을그리게 되고, 각 꼭짓점은 유연한 곡선으로 이어지며 형태를 이룹니다. 


// 기본 세팅 부분

int formResolution = 15; // 출력형태 해상도설정

float[] x = new float[formResolution]; // formResolution에서 설정한 수 만큼 배열 생성

float[] y = new float[formResolution]; // formResolution에서 설정한 수 만큼 배열 생성


int stepSize = 2; // stepSize의 크기는 원의 흔들림 정도를 설정합니다.(높을수록 형태변형이 많아짐)


float initRadius = 150;

float centerX, centerY;










void setup(){

...

//초기시작점의 위치는 디스플레이의 중간지점입니다.

centerX = width/2;

centerY = height/2;



float angle = radians(360/float(formResolution));


//agent의 시작위치는 '원의 점'으로 계산되고 배열 x와 y에 저장됩니다.

for(int = 0; i < formResolution; i++){

x[i] = cos(angle*i) * startRadius;

y[i] = sin(angle*i) * startRadius;

}

...

}








void mousePressed() {


  //마우스포지션에 의해 위치 초기화됩니다.

  centerX = mouseX; 

  centerY = mouseY;


  //마우스포지션에 의해 위치 초기화됩니다.

  float angle = radians(360/float(formResolution));

  float radius = initRadius * random(0.5, 1.0);


  for (int i=0; i<formResolution; i++) {

    x[i] = cos(angle*i) * radius;

    y[i] = sin(angle*i) * radius;

  }

}


mousePressed()함수를 활용하여 "마우스클릭"을 기준으로 새로운 값으로 초기화할 수있도록 합니다. 


mousePressed()는 draw()함수내에서 적용해야만 프로세싱이 실행되는 동안 사용자의 클릭을 감지합니다. 

draw()밖에서 적용할 경우 mousePressed()함수는 한번만 호출됩니다.








void draw(){


/*

마우스위치로의 이징(easing)부분 

매 프레임마다 agent위치와  마우스위치간의 거리가 계산되고, 작은 값(여기서는 0.01을 말합니다)에 의해 곱해집니다. 곱해진 값은 다시 위치값에 더해집니다.

*/

if( mouseX != 0 || mouse Y != ){

center X += (mouseX-centerX) * 0.01;

center Y += (mouseY-centerY) * 0.01;

}


// stepSize의 범위만큼의 랜덤값을 x와 y배열에 더해줍니다.

for(int i = 0 ; i < formResolution; i++){

x[i] +=  random(-stepSize, stepSize);

y[i] += random(-stepSize, stepSize);

// ellipse(x[i], y[i], 5, 5);

}


...

beginShape();

curveVertex(x[formResolution-1]+centerX, y[formResolution-1]+centerY);


for(int i = 0; i < formResolution; i++){

curveVertex( x[i] + centerX,  y[i] +  centerY );

}


curveVertex(x[i] + centerX, y[0] + centerY);

curveVertex(x[1] + centerX, y[1]+ centerY);



endShape();

}


**유의사항

beginShape()와 endShape()는 for구문이 종료된 이후에 포함시켜야 합니다.

 물론, for구문 안에 beginShape()와 endShape()를 위치시킨다해도 실행은 됩니다. 그러나, 우리가 원하는 결과가 나오지 않게 됩니다.





위 사진은 beginShape()와 endShape()를 for()구문안에 함께 넣었을때의 결과화면입니다. 에러가 발생하지는 않았지만, 이렇게되면 우리가 그리고자했던 형태의 도형을 얻을 수 없습니다. 자세한 내용은 아래의 사진에서 살펴보도록 하겠습니다.







먼저, 앞서 말씀드리는 문제의(?)화면입니다. beginShape()와 endShape()를 for()구문안에 넣은 후 결과창입니다. 이렇게되면 프로세싱에서는 for구문에서 설정한 횟수만큼 "도형시작 - 적용 - 도형끝"의 형태를 반복하게 됩니다. 간단히말해서 매 반복마다 다른 도형을 그리는 것입니다. (물론 이것이 잘못된 방법은아니나, 이 예제에서 그리고자했던것은 각 포인트가 연결되어 이루어지는 형태이기때문에, 반복문으로 매번 도형시작과 끝을 선언해서는 안되는 것입니다.)






위 사진은 for()구문 밖에 beginShape()와 endShape()를 적용한 화면입니다. 이런 구조로 만들어야지만이 우리가 원했던 형태의 도형을 프레임당 하나씩 그려낼 수 있습니다. 










vertex()와 curveVertex()의 비교


다음으로 살펴볼 것은 vertext()와 curveVertex()입니다. 기본적으로 위에서 작성한 코드에서는 curveVertex()를 사용했지만, vertex()로 바꾸어 적용해도됩니다. vertex의 사전적의미는 "꼭짓점"입니다. 즉 vertex()나 curveVertex()는 "먼저 꼭짓점을 그리고 그 꼭짓점들을 잇는 작업"이라고 생각하면 쉽습니다. 








이번 예제에서는 기본적으로 원의 형태로 x와y배열값으로 지정했음에도 vertex()는 꼭지점 사이의 선이 직선으로 그려짐에따라 각 도형들의 모습에서 "각진"느낌이 듭니다. 


반면에, "curve"라는 말처럼 curveVertex()는 vertex()에 비해 유연한 형태로 그려지게 됩니다.