Notice
Recent Posts
Recent Comments
«   2024/05   »
1 2 3 4
5 6 7 8 9 10 11
12 13 14 15 16 17 18
19 20 21 22 23 24 25
26 27 28 29 30 31
Today
Total
관리 메뉴

만재송

[Cocos Creator] Spine 정복하기(4) - Bone, IK 본문

프로그래밍/COCOS Creator

[Cocos Creator] Spine 정복하기(4) - Bone, IK

만재송 2018. 12. 6. 11:19

Spine 의 JSON 파일 데이터를 살펴보면 여러 항목으로 구성되어 있습니다.




이번 포스팅에서는 Spine 애니메이션의 뼈대가 되는 bone 과 ik 에 대해 설명 하겠습니다.



Bone


Spine 애니메이션은 여러개의 뻐대로 이루어져 있습니다. 실제로 우리 눈에 보이는 Spine 이미지는 1개로 보여지지만 실제로는 여러 이미지가 Bone에 의해서 연결되어 있는것입니다. Spine 애니메이션도 Bone의 위치와 회전 등, 어떻게 하냐에 따라서 애니메이션이 달라지는 것입니다. 


 <- Spine Bones


즉, Bone 은 애니메이션을 하기위한 물리적인 기능을 하고 있습니다. 포지션 변경과 회전 같은 기능을 담당하고 있습니다. 또한 Bone 은 부모 자식 개념이 있습니다. Cocos Creator 에서도 자식은 부모의 영향을 받게되죠? Bone 도 똑같습니다. 부모가 회전을 하게 되면 자식도 같이 회전을 하게됩니다. 


그럼, Bone 에 접근하여 Spine 애니메이션을 조작하는 방법을 알아보겠습니다.



Bone 접근


원하는 Bone 을 접근하기 위해서는 findBone 메서드를 사용하면 됩니다. 하지만, 원하는 Bone 에 접근하기 위해서는 Bone 의 이름을 알아야합니다. 2가지 방법이 있는데 첫번째는 Spine 애니메이션 제작자한테 각각의 Bone 이름(Bone 의 이름은 Spine 애니메이션 제작자가 설정합니다.)에 대해 여쭤보는 것입니다. 두번째 방법은 SkeletonData 를 콘솔에 찍어보는 방법입니다. 아래 이미지는 Bone 데이터를 나타냅니다.



콘솔로 확인하는 것이 간단하지만 어느 Bone 에 맞는 이름인지는 확인을 해봐야 합니다. 그래서 사전에 Spine 애니메이션 제작자와 협의를 해서 Bone 의 이름을 정하는 방법을 추천드립니다.


이제 Bone 이름도 알았으니, 한번 접근해 보겠습니다.


this.torso = this.spine.findBone("torso"); // 몸통 Bone에 접근
console.log(this.torso);


간단하게 접근이 가능합니다. 콘솔에 확인해보시면 Bone 이 가지고 있는 정보들을 확인할 수 있습니다.



Bone 조작


모든 조작은 bone 객체에 있는 data 프로퍼티 객체를 통해 조작합니다. (bone 객체에 있는 프로퍼티는 변경을 해도 값이 변하지 않았습니다.) data 객체를 살펴보면 이동을 담당하는 x,y 와 회전인 rotation, 스케일 변경까지도 할 수 있습니다. 



접근도 했으니 먼저 torso bone 을 움직여 보겠습니다. 매 프레임마다 호출되는 update 함수를 채워보겠습니다.


update (dt) {
this.torso.data.x += 1; // 몸통 부분을 매프레임마다 1씩 이동
}


실행하면 매프레임마다 몸통 부분이 움직이는 모습을 확인할 수 있습니다.




이번엔 몸을 회전시켜보겠습니다.


update (dt) {
this.torso.data.rotation += 1; // 몸통 부분을 매프레임마다 1씩 회전
}


여기서 중요한 부분은 몸통 Bone 만 움직였을 뿐인데 다른 하위 Bone 들도 움직이는 모습을 볼 수 있습니다. 이게 위에서 말한 자식은 부모의 영향을 받는다는 것입니다. 조작을 할 때 부모 자식 관계를 잘 확인하고 사용하면 될 것 같습니다.



IK


보통 사용하는 애니메이션 방식은 FK(forward kinematics)라는 하양식 접근 방식을 사용합니다. 팔이 회전을 하면 팔 위쪽이 먼저 회전을 하고 아래쪽이 회전하고 그다음 손의 위치가 결정됩니다. 그럼 반대로 손의 위치에 따라서 팔의 바라보는 위치가 결정되는 방법은 없을까요? 아래 닭처럼 말이죠.



그 방법이 IK(inverse kinematics) 입니다. IK 는 FK와 반대로 상향식 접근 방식을 사용합니다. IK를 설정한 Bone 은 위의 닭처럼 IK의 포인트만 바라보게 됩니다. 예제를 통해 IK를 사용하는 방법을 알아보겠습니다.


먼저 IK 가 있는 Spine 으로 변경을 하고, skeletonData 를 콘솔에 찍어서 IK 를 확인합니다. (skeletonData -> _skeletonJson -> ik)



여러 IK 가 있네요. 그중 다리를 한번 움직여 보겠습니다. IK 도 똑같이 Bone 에 속해 있기 때문에 findBone 으로 접근합니다.


let leg = this.spine.findBone("target_leg_r");


테스트는 마우스가 이동하는 방향으로 다리도 바라보게 구현해보겠습니다. 


// 마우스 move 이벤트
this.node.parent.on(cc.Node.EventType.MOUSE_MOVE, (event) => {
// 마우스의 포지션을 해당 노드의 포지션으로 변환
let pos = this.node.convertToNodeSpaceAR(event.getLocation());

// leg Bone(IK) 의 포지션 변경
leg.data.x = pos.x;
leg.data.y = pos.y;
});


테스트를 원할하게 하기위해 마우스 move 이벤트를 구현하겠습니다. 다음 현재 마우스의 포지션을 받아서 IK에 현재 포지션값을 적용하겠습니다.


원래대로라면 마우스가 이동하는곳으로 다리도 이동하겠지만, IK 는 다릅니다. 아래결과를 보시면 마우스가 이동하는 방향에 따라서 다리 끝부분이 바라보게 됩니다. 이와 같은 방법으로 게임을 만들때 캐릭터가 현재 마우스 위치를 바라보거나, 총을 겨누거나 하는 방식으로 만들 수 있게 됩니다.


Comments