読者です 読者をやめる 読者になる 読者になる

俺とプログラミング

某IT企業でエンジニアをしてます。このブログではプログラミングに関わることを幅広く発信します。

【libGDX入門】Actionの使い方

libGDXでのActionの使い方について紹介します。 Actionとは、Actorに一定の動作を行わせる仕組みです。 libGDXでは標準で様々なアクションが用意されています。 例えば、移動、回転、スケーリング、色の変化、フェードインなどです。 これらのActionを用いることで、かっこいい動作が簡単に表現できます。

基本的な使い方

ActionはActorにaddActionで追加すると同時に始まります。 ただし、renderでActorのactメソッドが毎フレーム呼ばれる事が前提です。
以下のコードを実行した直後、actorは座標(0,0)に2秒間で移動します。 Actionsクラスに標準アクションが用意されています。

Action action = Actions.moveTo( 0, 0, 2.0f);
actor.addAction(action);

Actionを使う上で大事なこと

  • ActionはActorに追加した直後から始まる
  • Actionは目的を達成したら自動で消える
  • Actionは実行する時間を指定できる

これから、特に重要なActionを紹介していきます。Actionの一覧は公式APIにあります。

moveTo, moveBy(移動)

/* (x, y)までtime秒で移動 */
Actions.moveTo( x, y, time );
/* (x, y)だけtime秒で移動 */
Actions.moveBy( x, y, time );

faceIn, fadeOut(透過)

/* time秒でalpha値が1に変化 */
Actions.fadeIn( time );
/* time秒でalpha値が0に変化 */
Actions.fadeOut( time );

scaleTo, scaleBy(スケーリング)

これらのActionはスケーリングに対応します。利用する際には、どの点を軸として拡大、縮小を行うのかを考える必要があります。デフォルトでは、画像の左端を原点として、スケーリングを行います。 これを中心にするには、以下のように幅と高さを2で割るのが簡単です。

actor.setOrigin(actor.getWidth()/2, actor.getHeight()/2);
/* time秒で(x, y)倍に変化 */
Actions.scaleTo( x, y, time );
/* time秒で(現在のx倍率 + x, 現在のy倍率 + y)倍に変化 */
Actions.scaleBy( x, y, time );

scaleByでは、縮小したいときはマイナスの値を指定します。

rotateTo, rotateBy(回転)

回転動作も、スケーリングと同様にどの点を軸に回転するかを意識する必要があります。

/* time秒でx度に向かって回転 */
Actions.rotateTo( x, time );
/* time秒でx度だけ回転 */
Actions.rotateBy( x, time );

sequence(連続して実行)

sequenceは連続してアクションを実行したい時に使えます。アクションは何個でも繋げられます。

/* action1、action2の順に実行 */
Actions.sequence( action1, action2 );

例えば2秒で右に100移動したあと、1秒で上に50移動する、という動作は以下のように記述します。

Actions.sequence(
    Actions.moveBy( 100, 0, 2.0f),
    Actions.moveBy( 0, 50, 1.0f));

parallel(並列で実行)

/* action1とaction2を同時に実行 */
Actions.paralell( action1, action2 );


例えば(0.1, 0.1)にスケーリングしながら、フェードアウトするという動作は以下のように記述します。

Actions.parallel(
    Actions.scaleTo(0.1f,0.1f, 1.0f),
    Actions.fadeOut(1.5f));

上記のように実行時間が食い違っていた場合、全てのアクションが終了するまで終わりません。

forever(無限ループ)

普通アクションが終了すると、そのアクションは自動で消えますが、ずっと続いてほしい時もあると思います。そんな時、foreverが使えます。

/* actionを無限に実行 */
Actions.forever( action );

例えば、4隅を永遠に回り続けるような動作は以下のように書けます。

Actions.forever(
    Actions.sequence(
        Actions.moveTo( 50, 0, 0.5f ),
        Actions.moveTo( 50, 50, 0.5f ),
        Actions.moveTo( 0, 50, 0.5f ),
        Actions.moveTo( 0, 0, 0.5f )));

Interpolation(非線形な変化)

Interpolationは移動、回転、透過、スケーリングなどの基本アクションに華をそえます。 これまでの線形で単調な変化ではなく、動作に非線形な変化を与えることができます。 使いかたは簡単で、これまでのActionの引数の最後にInterpolationの種類を与えるだけです。

Actions.moveTo( x, y, time, Interpolation.bounceIn );

いろいろな変化の仕方があるので遊んでみてください。
Interpolationの一覧は公式APIに載っています。

removeActor(Actorの削除)

このActionはActorをStageやGroupなどの親グループから削除します。 これは例えば敵キャラが消滅する時などに便利です。

/* 透明化した直後に、親グループから自身を削除 */
actor.addAction(
    Actions.sequence(
        Actions.fadeOut(0.5f),
        Actions.removeActor()));

Actionの終了判定

Actionが終了した時になにか処理を行いたい場合、下記のようにsequenceとrunを利用することで実現できます。

Actor.addAction(
    Actions.sequence(
        Actions.moveTo(0, 0),
        Actions.run(new Runnable() {
            @Override
            public void run() {
                /*ここにアクション終了時のコードを書きます*/
                System.out.println("action complete");
            }
        })));

Actionsの省略

標準Actionはstaticメソッドなので、static importすることでActionsという記述を省略できます。 同様にInterpolationも省略可能です。

import static com.badlogic.gdx.scenes.scene2d.actions.Actions.*;
import static com.badlogic.gdx.math.Interpolation.*;
---
actor.addAction(moveTo(x, y, time, bounceOut));

複雑なアクション

Actionには無限の組み合わせがあります。これまで紹介してきたもので少し複雑なActionを構成してみました。このActionが一体どんな動作をするのかは動画をご覧ください。

forever(
    parallel(
        rotateBy(360, 3.2f),
        sequence(
            parallel(
                moveTo( 200, 0, 0.8f, bounceOut ),
                scaleTo( 0.5f, 0.5f, 0.8f, bounceOut )),
            parallel(
                moveTo( 200, 200, 0.8f, swingIn ),
                scaleTo( 1.0f, 1.0f, 0.8f, swingIn )),
            parallel(
                moveTo( 0, 200, 0.8f, circleOut ),
                fadeOut( 0.8f, circleOut )),
            parallel(
                moveTo( 0, 0, 0.8f, elasticIn ),
                fadeIn( 0.8f, elasticIn )))));

youtu.be

実行中のアクションの数を取得

実行中のアクションの数を知りたい時はgetActions()で現在のアクションのリストを取得できるので、sizeメソッドが使えます。

actor.getActions().size


Androidゲームプログラミング A to Z

Copyright © 2016 ttlg All Rights Reserved.