2014년 3월 4일 화요일

[일기] Box2D, 접합점, 개요

http://www.iforce2d.net/b2dtut/joints-overview를 참조하였다.

접합점은 두 강체를 서로 연결하기 위해 보통 쓰인다.

예를 들어, 경첩이나, 피스톤, 밧술, 바퀴, 도르레, 차량, 사슬과 같은 것들을 만들 때는 강체간 연결되어야 하기 때문에 이 때 강체들을 연결하기 위해 접합점이 쓰이게 된다.

 종류는

  Revolute   : 회전 고정점, 두 강체는 이 점을 중심으로 회전
  Distance   : 거리 고정점, 두 강체는 고정된 거리만큼 떨어짐
  Prismatic  :  두 강체는 고정된 상대적 각도만큼 고정되어 있으며, 축을 따라 이동함
  Line(Wheel) : Revolute와 Prismatic의 결합, 탈것 모델링에 유용하다.
  Weld        : 두 강체들을 같은 방향으로 잡아둔다.
  Pulley       : 계의 특점 점으로부터 두 강체간의 거리를 유지시킨다. 두 점과 각각의 강체 사이의 거리의 합은 일정하다.
  Friction     : 두 강체 사이의 상대적 움직임을 줄인다.
  Gear         : 다른 접합점(Revolute, Prismatic)을 제어한다. 따라서 하나의 움직임에 다른 것이 영향을 받는다.
  Mouse      : 계 내에 위치시키기 위해 강체의 한 점을 당긴다. Testbed에서 우리가 물체를 마우스로 클릭했을 때 그 위치에 생기는 고정점이다.

 그런데 이러한 설명을 보고서는 도저히 모르겠다..


[revolute]
[prismatic]
[rope]
몇 개 이미지를 구해봤다. 

생성은 계 클래스를 통해 이루어진다. 강체나 고정체와 동일하게.

//set up the definition for a xxx joint
  b2xxxJointDef jointDef;
  jointDef.xxx = ...;
  
  //create the joint
  b2xxxJoint* joint = (b2xxxJoint*)world->CreateJoint( &jointDef );

 xxx는 각 접합점의 이름으로 바뀐다. CreateJoint에서 캐스팅을 함을 확인해야 했다.
 b2Joint 추상클래스 포인터를 리턴한다.

 추상클래스가 그 상위 클래스이므로 접합점들은 다음을 포함하여 여러가지를 공통적으로 갖는다.


bodyA - 필수사항으로 이 접합점에 합쳐질 강체
bodyB - 필수사항으로 이 접합점에 합쳐질 강체2
collideConnected - 이 접합점에 합쳐진 강체간 충돌할지에 대한 여부, 기본값 거짓

이와 같이 설정한다.
  jointDef.bodyA = upperLegBody;
  jointDef.bodyB = lowerLegBody;
  jointDef.collideConnected = false;

각 접합점별로 존재하는 특별한 설정 또한 존재한다.

 다음은 그것들 중 대략적인 것들이다. 각 접합점마다 약간씩 다르게 설정되나 유사한 개념들을 기록했다.

 anchor points
Typically a point on each body is given as the location around which the bodies must interact. Depending on 
the joint type, this point will be the center of rotation, the locations to keep a certain distance apart, etc.
joint limits
Revolute and prismatic joints can be given limits, which places a restriction on how far the bodies can
rotate or slide.
joint motors
Revolute, prismatic and line (wheel) joints can be given motor settings, which means that instead of spinning 
or sliding around freely, the joint acts as if it had it's own power source. The motor is given a maximum force or 
torque, and this can be used in combination with a target velocity to spin or slide bodies in relation to each other.
If the velocity is zero, the motor acts like a brake because it aims to reduce any motion between the bodies.

제거 역시 방식은 강체나 고정체와 동일하다.

world->DestroyJoint( myJoint );

단, 강체를 제거할 경우 그것과 연결된 접합점들도 같이 제거되므로 제거가 강체를 포함하여 동시에 이루어질 경우 순서에 유의해야 한다.

//BAD!
  world->DestroyBody( body1 ); // myJoint becomes invalid here
  world->DestroyJoint( myJoint ); // crash
  
  //OK
  world->DestroyJoint( myJoint );
  world->DestroyBody( body1 );

사용자 매뉴얼에 있는 암묵적 제거에대한 리스너를 사용해도 된다. 단 이때에는 사용자 데이터를 사용하여 구분을 해야 한다.


 접합점의 위치도 문제가 되는 경우가 있다고 한다. 일반적으로 가벼운 물체 위에 매우 무거운 물체가 올라와 있는 경우이다. 또 있다면 대표적으로 가벼운 재질로 된 체인에 상당히 무거운 물체가 달려 있는 경우이다.

 실제 상황이라면 아래 물체의 형태가 변하기 마련(전자는 깨지거나 납작해 지거나, 후자는 체인이 끊어지거나 늘어나거나)이다. 그러나, Box2D에서는 이러한 상황까지 시연해 주지는 않으므로 부자연스러운 상황이 나타나게 된다.

 해결법은 질량의 차이를 줄이는 것이다. 또한 가장 단순한 방식이다.



참말.. 실제 현실을 시연하기 위해 필요한 것들이 대체 몇개야....
그걸 표현하는 것도 참으로 대단허이..

댓글 없음:

댓글 쓰기