[cocos2d-x 3.0 beta2] Action 액션 사용
레이어에 붙여놓은 스프라이트를 조작하는 방법쯤 되겠다.
원하는 위치에 놓은것부터 옮기기, 회전시키기, 크기를 조정하기 등등 무수한 액션들이 존재한다.
얼마나 많은지는 아래 사이트를 참고하자. 우선 대충 훑어보기를 바란다. 뭐가 있는지 알아서 써먹을 수도 있지..
http://www.cocos2d-x.org/reference/native-cpp/V3.0beta2/dd/d0d/group__actions.html
보고나면 질린다..ㅡ.ㅡ
그래도 정리를 해야하니까...
스프라이트를 조작하는 거라고 했으니까, 대상 스프라이트가 있어야겠지.
Sprite* catSprite = Sprite::create("cat.png");
catSprite->setPosition( Point( 100, 100 ) );
this->addChile(catSprite);
라고 하나 만들어서 레이어에 붙였다고 가정하자.
cocos2d-x 가 제공하는 많은 액션들을 만들어서 저 스프라이트에 적용하는 방법은 아래와 같다.
catSprite->runAction(액션변수명);
runAction 함수를 호출하기 전에 액션을 만들어둬야하는건 당연하다.
대부분의 액션은 ::create() 로 만들수있다.
MoveTo 라는 액션의 경우 아래처럼 만들수 있다.
auto actionTo = MoveTo::create(2, Point( 200, 200));
create 함수내의 값들은 매뉴얼을 참고하면 되겠다. 설명하자면 2초 동안 현재의 좌표에서 (200, 200) 좌표로 이동시키는 액션이다.
아래처럼하면 현재, 초기 위치 (100,100)에 있던 고양이가 2초 걸려서 (200,200) 으로 이동을 한다.
catSprite->runAction(actionTo);
종류가 많아서 질리지 사용하기에는 무지 쉽다.
MoveTo 액션처럼 사용할 수 있는 액션들이 무지 많다. 저렇게 만들어 쓰면 된다.
Sequence
다른 욕심이 생길 수 있다.
여러개의 액션들을 쭈욱~ 이어서 동작시키려면 어떻게 하면 될까?
여러개의 액션이 순차적으로 실행되기를 원할 때 사용하는 것을 Sequence 라는 액션이 있다.
Sequence는 액션 클래스이긴 하지만 스프라이트를 조작하지는 않는다. 단지 다른 액션들을 여러개 묶어줄 수 있다.
auto actionTo1 = MoveTo::create(1, Point( 100, 100));
auto actionTo2 = MoveTo::create(2, Point( 200, 200));
auto seq = Sequence::create(actionTo1, actionTo2, NULL);
catSprite->runAction(seq);
1초만에 (100,100)으로 간 후, 다시 2초 걸려서 (200,200) 으로 이동하는 액션 두개를 묶어서 seq 라는 시퀀스 액션으로 만들었다.
묶어놓은 액션은 순서대로 실행이 된다.
시퀀스로 액션을 묶을 때, 마지막에 NULL 을 넣어줘야한다. 더 묶어줄 거 없다고 알려주는거라 생각하자..ㅎ
Spawn
또 다른 욕심이 생길 수 있다.
순서대로 액션이 이어지는것이 아니라, 2개 이상의 액션이 동시에 일어나도록 하고 싶으면 우째야할까?
고양이가 빙글빙글 회전하면서 어느 좌표로 이동하도록 만들고 싶을 수도 있지않을까?
이를 위한 Spawn 이라는 액션 클래스가 있다.
auto actionTo1 = MoveTo::create(2, Point( 100, 100));
auto rotate1 = RotateTo::create(2, 180);
auto spawn = Spawn::create(actionTo1, rotate1, NULL);
catSprite->runAction(seq);
2초 걸려 (100,100)으로 이동하는 액션과 2초동안 180도 회전하는 액션이 동시에 발생한다. 휘~익 뒤집어 지면서 이동하는것이다.
Repeat , RepeatForever
다른 특이 액션들이 몇 개 있다.
Repeat와 RepeatForever 는 단일 액션이든지, 시퀀스던지, 스폰이던지, 반복시킬 수 있다.
아래처럼 하면 먼저 만들어놓은 seq 액션을 3번 반복한다.
auto rep1 = Repeat::create(seq, 3);
catSprite->runAction(rep1);
물론 아래처럼 하면 무한 반복한다.
auto rep1 = RepeatForever::create(seq);
catSprite->runAction(rep1)DelayTime
또 하나 독특한 액션, DelayTime 이 있다.
1초 대기한 후에 이동을 시키고 싶으면 이 1초 대기를 DelayTime 을 써서 만들어 줄 수 있다.
auto actionTo1 = MoveTo::create(1, Point( 100, 100));
auto delay1 = DelayTime::create(1);
auto seq = Sequence::create(delay1, actionTo1, NULL);
catSprite->runAction(seq);
Reverse
모든 액션은 그 반대의 액션을 쉽게 가져올 수 있다.
만약 현재 위치에서 (100,100) 만큼 이동했다가 다시 원래 자리로 돌아오기를 바랄 경우, 액션 두개를 만들어도 되지만, 돌아오는 액션은 가는 액션의 반대라고 바로 만들어줄 수가 있다는 거다.
auto actionGo1 = MoveBy::create(1, Point( 100, 100));
auto actionCome1 = actionGo1->reverse();
여기까지의 내용만 알아도 온갖 종류의 액션을 만들어 사용할 수 있을거 같다.
콜백함수
하지만, 여기서 더 필요한 것이 있다. 바로 콜백 함수다.
게임을 개발하다 보니, 액션이 끝난 시점에서 무언가를 실행시키고 싶을 경우가 많이 있다. 콜백함수를 사용하면 아주 유용하다.
"액션이 종료되면 이 함수를 실행해라!" 라고 설정을 하는거다.
위에서 본 시퀀스 예이다.
auto actionTo1 = MoveTo::create(1, Point( 100, 100));
auto actionTo2 = MoveTo::create(2, Point( 200, 200));
auto seq = Sequence::create(actionTo1, actionTo2, NULL);
catSprite->runAction(seq);
actionTo2 까지 실행이 되어 고양이가 (200,200)으로 이동이 완료된 시점에 고양이 소리를 내고 싶다고 가정하자..(예가 좀 그렇지만..뭐..)
auto actionTo1 = MoveTo::create(1, Point( 100, 100));
auto actionTo2 = MoveTo::create(2, Point( 200, 200));
auto cbSound = CallFunc::create( CC_CALLBACK_0(GameLayer::putSound, this) );
auto seq = Sequence::create(actionTo1, actionTo2, cbSound, NULL);
catSprite->runAction(seq);
...
void GameLayer::putSound()
{
// 소리 출력 코드
}
CallFunc 를 이용해서 콜백함수를 만들고 시퀀스에다가 혹은 스폰에다가 저렇게 추가해주면 된다.
그런데, 콜백함수에 인자를 주고 싶으면 어떻게 해야하나??
스프라이트등 Node를 전달하거나, 추가 값을 전달하고 싶을 경우, 아래처럼 CallFunc를 사용하고,
CallFunc::create( CC_CALLBACK_0(GameLayer::callback1,this)),
CallFunc::create( CC_CALLBACK_0(GameLayer::callback2,this, sprite1)),
CallFunc::create( CC_CALLBACK_0(GameLayer::callback3,this, sprite1, 12345)),
콜백함수의 구현은 아래처럼 하면 되겠다.
void GameLayer::callback1()
{
...
}
void GameLayer::callback2(Node* sender)
{
...
}
void GameLayer::callback3(Node* sender, long data)
{
...
}
CallFuncN 도 있습니다. N이 노드를 의미한다는데, 콜백함수의 첫번째 인자로 액션을 실행하고 있는 자기 자신을 넘겨주는거 같습니다.
아래처럼 콜백함수를 만들어서 시퀀스에다가 끼워넣어주면 되겠죠.
CallFuncN::create( CC_CALLBACK_1(GameLayer::callback, this)), NULL);
실제 함수 구현은 아래의 모양을 하게 됩니다.
void GameLayer::callback(Node* sender )
{
// sender 는 액션을 실행한 바로 그녀석!
}
CallFunc 랑 좀 헤깔리네요.
이상.
'소프트웨어 > cocos studio' 카테고리의 다른 글
cocos-2dx js note (0) | 2016.11.09 |
---|---|
[cocos studio] sprite를 setPosition했는데 화면에 안보일때, (0) | 2016.02.24 |
[cocos studio] menu toggle에 대해서 (0) | 2016.02.23 |
[cocos studio] CCLOG 로그찍어보기 (0) | 2016.02.12 |
[cocos studio] 세로 화면에서 개발하기 (0) | 2016.02.12 |