渋谷ほととぎす通信

エンジニア社長によるUnityとAIのブログ & エンジニアの生存戦略

【知らないと事故る】DOTweenコールバック関数の実行順

【知らないと事故る】DOTweenコールバック関数の実行順

こんにちは、Unityエンジニアのオオバです。

お悩みさん
お悩みさん
  • DOTweenのコールバック関数って多くない?
  • コールバック関数の実行順が分からない
  • オオバ
    オオバ
    本記事ではこれらの悩みを解決します。

    DOTweenはUnityでアニメーションをスクリプトから実装する時に超絶便利なアセットです。ゲーム中の演出やUIアニメーションを実装する時に大活躍します。

    演出はテンポが重要なのですが、ロジック面ではイベント管理が重要です。

    例えばアニメーションの

    • 開始タイミング
    • 更新タイミング
    • 終了タイミング
    • 中断タイミング

    など、様々なタイミングで異なる処理を挟む必要が出てきます。これらを OnStart(開始タイミング)OnComplete(終了タイミング) を使って実装します。

    実はDOTweenのコールバック関数は実行順の把握が非常に重要です。主要なコールバック関数は8種類もあり 実行順を正しく理解していないと不具合に繋がります。

    ぜひこの記事を参考に実行順を理解していきましょう。

    DOTweenを使ってこれからスクリプトでアニメーションを実装していきたい方はこちらの記事を参考にしてみてください。

    👉DOTweenの教科書を読んでUnityアニメーションをプログラミングしてみよう!

    DOTweenコールバック関数の使い方

    そもそもDOTweenのコールバック関数の使い方について解説します。いろんなコールバックが実装されていますが、よく使うOnComplete(Tween完了時のコールバック)を例に解説していきます。次のコードを見てみましょう。

    transform.DOLocalMove(new Vector3(1f, 0, 0), 0.5f)  
        .OnComplete(()=>Debug.Log("Tween完了"));  
    

    Tweenに対してOnComplete関数を実行します。使い方は簡単で引数に関数を渡して使うのです。

    また次のコードのように一度Tweenを変数に格納してOnCompleteを指定することも可能です。

    var tween = transform.DOLocalMove(new Vector3(1f, 0, 0), 0.5f);  
    tween.OnComplete(()=>Debug.Log("Tween完了"));  
    

    こんな感じDOTweenのコールバックを使用していきます。

    UniTaskを使うと更に便利に使えるDOTween

    DOTweenはUniTaskと連携して使えます。UniTaskとはUnityで非同期処理を実装する時によく使われるアセットです。

    例えばアニメーションの完了を待機して次の処理を実行するという何かを待機する処理はまさに非同期処理です。


    ↑上の動画はUniTaskとDOTweenを使ったサンプルです。3人のTweenを待機した後全員でジャンプするように実装しています。詳しくは↓こちらの記事を参考にしてみてください。

    またUniTaskを使うとDOTweenのコールバックは次のように書き直せます。

    await transform.DOLocalMove(new Vector3(1f, 0, 0), 0.5f).ToUniTask();  
    Debug.Log("Tween完了");  
    

    awaitToUniTask を使うことでOnCompleteを使うことなく実装できます。上から順に処理を書くことができるため可読性の高いコードになります。

    しかしUniTaskは中断処理に気をつけないといけません。UniTaskとDOTweenのレン刑事も同じです。正しく中断処理を実装しないと不具合につながるので、次の記事を参考にUniTaskの中断処理を確認してみてください。

    8種類のDOTweenコールバック

    ではDOTweenのコールバック実行順位ついて具体的に解説していきます。

    ちなみにDOTweenのコールバック関数は主要なところでいうと8種類あります。表にまとめてみました。

    コールバック関数内容
    OnStartTweenの開始タイミング
    OnPlayTweenの再生タイミング
    OnUpdateTweenの更新タイミング
    OnPauseTweenポーズタイミング
    OnStepCompleteTweenのリピートタイミング
    OnCompleteTweenの終了タイミング
    OnKillTweenの終了タイミング
    OnRewindTweenのリスタートタイミング

    これらがどういう順番で実行されるのか解説していきます。

    DOTweenコールバックの基本的な実行順序

    DOTweenのコールバック順を調査するために次のような検証コードを用意しました。

    void Start()  
    {
        var tween = transform.DOLocalMoveX (2f, 1f)  
            .OnStart (() => Debug.Log ("OnStart"))  
            .OnPlay (() => Debug.Log ("OnPlay"))  
            .OnKill (() => Debug.Log ("OnKill"))  
            .OnComplete (() => Debug.Log ("OnComplete"))  
            .OnPause (() => Debug.Log ("OnPause"))  
            .OnRewind (() => Debug.Log ("OnRewind"))  
            .OnStepComplete (() => Debug.Log ("OnStepComplete"))  
            .OnUpdate (() => Debug.LogWarning ("OnUpdate"))  
            .OnWaypointChange (x => Debug.Log ("OnWaypointChange" + x));  
    }
    

    上記のソースコードを実行すると次のような出力結果になります。

    1. OnStart
    2. OnPlay
    3. OnUpdate(毎フレーム実行)
    4. OnStepComplete
    5. OnComplete
    6. OnKill

    OnStart から始まり OnKill で終わります。これがDOTweenコールバックの基本的な実行順です。

    さてここから様々なパターンでTweenの再生や停止させて挙動を確認していきます。

    オオバが執筆したDOTweenの教科書では動画でよりわかりやすくDOTweenのコールバックを理解できるようになっています。

    DOTweenを深く学んでいきたい方はぜひチェックしてみてください。
    ※ちなみに↑上記の動画は有料ページのチラ見せです。

    DOTweenの中断(Kill)と完了(Complete)

    まずはTweenの中断と完了におけるDOTweenコールバックの実行順をチェックしていきます。

    結論から言うと 呼ばれる順番は基本的に同じ ですが 呼ばれるコールバックと呼ばれないコールバックが登場する ため注意が必要です。

    次の4つのパターンで確認していきます。

    Tweenの中断と完了によるコールバックの差分

    ①中断 Kill(false)

    ②中断 Kill(true)

    ③完了 Complete(false)

    ④完了 Complete(true)

    DOTweenの中断Kill(false)

    Tween中断による挙動を確認していきます。Tweenの中断は Kill メソッドを使います。Killメソッドにはbool型の引数を渡せるのがポイントです。 引数によって実行されるコールバックが変わる ため注意してください。

    具体的には次のコードを実行していきます。

    1秒かけて動作するDOTweenを実行して0.5秒のタイミングで中断させます。

    IEnumerator Start()  
    {
        var tween = transform.DOLocalMoveX (2f, 1f)  
            .OnStart (() => Debug.Log ("OnStart"))  
            .OnPlay (() => Debug.Log ("OnPlay"))  
            .OnKill (() => Debug.Log ("OnKill"))  
            .OnComplete (() => Debug.Log ("OnComplete"))  
            .OnPause (() => Debug.Log ("OnPause"))  
            .OnRewind (() => Debug.Log ("OnRewind"))  
            .OnStepComplete (() => Debug.Log ("OnStepComplete"))  
            .OnUpdate (() => Debug.LogWarning ("OnUpdate"))  
            .OnWaypointChange (x => Debug.Log ("OnWaypointChange" + x));  
    
        yield return new WaitForSeconds(0.5f);  
        // 中断メソッドにfalseを代入  
        tween.Kill(false);  
    }
    

    すると、次のような結果になります。

    1. OnStart
    2. OnPlay
    3. OnUpdate(毎フレーム実行)
    4. OnKill

    基本形から変わったのは、OnStepCompleteOnComplete が呼ばれなくなりました。

    DOTweenの中断Kill(true)

    次はTweenの中断メソッドKillの引数にtrueを代入して変化を確認してみましょう。具体的には次のコードを実行します。

    IEnumerator Start()  
    {
        var tween = transform.DOLocalMoveX (2f, 1f)  
            .OnStart (() => Debug.Log ("OnStart"))  
            .OnPlay (() => Debug.Log ("OnPlay"))  
            .OnKill (() => Debug.Log ("OnKill"))  
            .OnComplete (() => Debug.Log ("OnComplete"))  
            .OnPause (() => Debug.Log ("OnPause"))  
            .OnRewind (() => Debug.Log ("OnRewind"))  
            .OnStepComplete (() => Debug.Log ("OnStepComplete"))  
            .OnUpdate (() => Debug.LogWarning ("OnUpdate"))  
            .OnWaypointChange (x => Debug.Log ("OnWaypointChange" + x));  
    
        yield return new WaitForSeconds(0.5f);  
        // 中断メソッドにtrueを代入  
        tween.Kill(true);  
    }
    

    すると結果はこうなります。

    1. OnStart
    2. OnPlay
    3. OnUpdate(毎フレーム実行)
    4. OnComplete
    5. OnKill

    ポイントは OnComplete の有無です。今回の Kill(true) ではOnKill、OnComplete共に実行される点に注意しましょう。

    DOTweenの完了Complete(false)

    次にTweenの途中で完了メソッドCompleteを実行してみます。先のKillとCompleteの違いはTweenの進捗具合です。Killは実行タイミングで中断しますがCompleteは最後まで実行された状態にジャンプします。

    またCompleteはKill同様bool型の引数が代入できるため「false」を設定して結果を確認していきましょう。具体的には次のコードを実行していきます。

    IEnumerator Start()  
    {
        var tween = transform.DOLocalMoveX (2f, 1f)  
            .OnStart (() => Debug.Log ("OnStart"))  
            .OnPlay (() => Debug.Log ("OnPlay"))  
            .OnKill (() => Debug.Log ("OnKill"))  
            .OnComplete (() => Debug.Log ("OnComplete"))  
            .OnPause (() => Debug.Log ("OnPause"))  
            .OnRewind (() => Debug.Log ("OnRewind"))  
            .OnStepComplete (() => Debug.Log ("OnStepComplete"))  
            .OnUpdate (() => Debug.LogWarning ("OnUpdate"))  
            .OnWaypointChange (x => Debug.Log ("OnWaypointChange" + x));  
    
        yield return new WaitForSeconds(0.5f);  
        // 完了メソッドにfalseを代入  
        tween.Complete(false);  
    }
    

    結果は以下のようになりました。

    1. OnStart
    2. OnPlay
    3. OnUpdate
    4. OnComplete
    5. OnKill

    Kill(true) と同じ結果です。

    DOTweenの完了Complete(true)

    次に完了メソッドCompleteの引数にtrueをセットして挙動を確認していきます。

    IEnumerator Start()  
    {
        var tween = transform.DOLocalMoveX (2f, 1f)  
            .OnStart (() => Debug.Log ("OnStart"))  
            .OnPlay (() => Debug.Log ("OnPlay"))  
            .OnKill (() => Debug.Log ("OnKill"))  
            .OnComplete (() => Debug.Log ("OnComplete"))  
            .OnPause (() => Debug.Log ("OnPause"))  
            .OnRewind (() => Debug.Log ("OnRewind"))  
            .OnStepComplete (() => Debug.Log ("OnStepComplete"))  
            .OnUpdate (() => Debug.LogWarning ("OnUpdate"))  
            .OnWaypointChange (x => Debug.Log ("OnWaypointChange" + x));  
    
        yield return new WaitForSeconds(0.5f);  
        // 完了メソッドにtrueを代入  
        tween.Complete(true);  
    }
    

    すると結果は次のようになります。

    1. OnStart
    2. OnPlay
    3. OnUpdate(毎フレーム実行)
    4. OnStepComplete
    5. OnComplete
    6. OnKill

    Complete(false) との違いは OnStepCompleteの有無 です。 Complete(true) を実行するとOnStepCompleteも呼ばれる点に注意しましょう。

    DOTweenのポーズ(Pause)と再開(Play or Restart)、

    次にTweenのポーズと再開によるコールバック挙動の違いを確認していきます。Tweenのポーズってあまり使われないと思われがちですが、ゲーム開発中はゲームの一時停止機能を実装する時に必要となります。

    再びTweenを再開する時にPlayまたはRestartでアニメーションを再生するのですが、それぞれコールバックの挙動が変わってくるため注意しましょう。

    DOTweenの途中でポーズ(Pause)

    まずはTweenの途中でポーズしてみましょう。具体的には次のコードを実行してみます。

    IEnumerator Start()  
    {
        var tween = transform.DOLocalMoveX (2f, 1f)  
            .OnStart (() => Debug.Log ("OnStart"))  
            .OnPlay (() => Debug.Log ("OnPlay"))  
            .OnKill (() => Debug.Log ("OnKill"))  
            .OnComplete (() => Debug.Log ("OnComplete"))  
            .OnPause (() => Debug.Log ("OnPause"))  
            .OnRewind (() => Debug.Log ("OnRewind"))  
            .OnStepComplete (() => Debug.Log ("OnStepComplete"))  
            .OnUpdate (() => Debug.LogWarning ("OnUpdate"))  
            .OnWaypointChange (x => Debug.Log ("OnWaypointChange" + x));  
    
        yield return new WaitForSeconds(0.5f);  
        // ポーズ  
        tween.Pause();  
    }
    

    すると以下の結果になります。

    1. OnStart
    2. OnPlay
    3. OnUpdate
    4. OnPause

    ポーズをすると OnPause が実行されます。当然ですがTweenが中断、完了していないため、OnComplete、OnKillは呼ばれません。

    DOTweenの途中でポーズ(Pause)後に再開(Play)

    ではTweenをポーズした後Playメソッドで再開してみましょう。次のコードを実行してみます。

    IEnumerator Start()  
    {
        var tween = transform.DOLocalMoveX (2f, 1f)  
            .OnStart (() => Debug.Log ("OnStart"))  
            .OnPlay (() => Debug.Log ("OnPlay"))  
            .OnKill (() => Debug.Log ("OnKill"))  
            .OnComplete (() => Debug.Log ("OnComplete"))  
            .OnPause (() => Debug.Log ("OnPause"))  
            .OnRewind (() => Debug.Log ("OnRewind"))  
            .OnStepComplete (() => Debug.Log ("OnStepComplete"))  
            .OnUpdate (() => Debug.LogWarning ("OnUpdate"))  
            .OnWaypointChange (x => Debug.Log ("OnWaypointChange" + x));  
    
        yield return new WaitForSeconds(0.5f);  
        // ポーズ  
        tween.Pause();  
    
        yield return new WaitForSeconds(0.5f);  
        // 再開  
        tween.Play();  
    }
    

    すると次のような結果になります。

    1. OnStart
    2. OnPlay
    3. OnUpdate(毎フレーム実行)
    4. OnPause
    5. OnPlay
    6. OnUpdate(毎フレーム実行)
    7. OnStepComplete
    8. OnComplete
    9. OnKill

    OnPause が呼ばれた後、再開時に OnPlay が実行されます。注意点として 再開時にOnStartは呼ばれないこと 。OnStartは初回しか実行されない点に注意しましょう。逆にOnPlayは何度も呼ばれます。

    DOTweenの途中でポーズ(Pause)後に再開(Restart)

    ポーズ後の再開メソッドをPlayからRestartに変えて挙動を確認していきます。具体的には次のソースコードを実行します。

    IEnumerator Start()  
    {
        var tween = transform.DOLocalMoveX (2f, 1f)  
            .OnStart (() => Debug.Log ("OnStart"))  
            .OnPlay (() => Debug.Log ("OnPlay"))  
            .OnKill (() => Debug.Log ("OnKill"))  
            .OnComplete (() => Debug.Log ("OnComplete"))  
            .OnPause (() => Debug.Log ("OnPause"))  
            .OnRewind (() => Debug.Log ("OnRewind"))  
            .OnStepComplete (() => Debug.Log ("OnStepComplete"))  
            .OnUpdate (() => Debug.LogWarning ("OnUpdate"))  
            .OnWaypointChange (x => Debug.Log ("OnWaypointChange" + x));  
    
        yield return new WaitForSeconds(0.5f);  
        // ポーズ  
        tween.Pause();  
    
        yield return new WaitForSeconds(0.5f);  
        // 再開  
        tween.Restart();  
    }
    

    すると結果は以下のようになりました。

    1. OnStart
    2. OnPlay
    3. OnUpdate(毎フレーム実行)
    4. OnPause
    5. OnUpdate(※1度だけ実行)
    6. OnRewind
    7. OnPlay
    8. OnUpdate(毎フレーム実行)
    9. OnStepComplete
    10. OnComplete
    11. OnKill

    Restartを使った再開はOnPlayではなく OnRewind が実行されます。Pause後に 1度だけOnUpdateが呼ばれる謎仕様 に注意です。

    DOTweenの途中で最初から再生(Restart)

    Tween再生後Restartで最初から再生させてみます。具体的には次のソースコードです。

    IEnumerator Start()  
    {
        var tween = transform.DOLocalMoveX (2f, 1f)  
            .OnStart (() => Debug.Log ("OnStart"))  
            .OnPlay (() => Debug.Log ("OnPlay"))  
            .OnKill (() => Debug.Log ("OnKill"))  
            .OnComplete (() => Debug.Log ("OnComplete"))  
            .OnPause (() => Debug.Log ("OnPause"))  
            .OnRewind (() => Debug.Log ("OnRewind"))  
            .OnStepComplete (() => Debug.Log ("OnStepComplete"))  
            .OnUpdate (() => Debug.LogWarning ("OnUpdate"))  
            .OnWaypointChange (x => Debug.Log ("OnWaypointChange" + x));  
    
    
        yield return new WaitForSeconds(0.5f);  
        // リスタート  
        tween.Restart();  
    }
    
    1. OnStart
    2. OnPlay
    3. OnUpdate(毎フレーム実行)
    4. OnRewind
    5. OnPause
    6. OnUpdate(毎フレーム実行)
    7. OnStepComplete
    8. OnComplete
    9. OnKill

    ポイントは ポーズしていないにも関わらずOnPauseが呼ばれること です。かなり引っかかりやすいため注意しましょう。

    DOTweenのループに関するコールバック挙動

    次にループしたTweenでコールバック挙動を確認していきます。Tweenのループはよく使います。例えばゲームタイトル画面内の「TAP TO START」はTweenをループさせて点滅アニメーションさせることが多いです。

    またタップするとTweenを中断して何か別の処理を実行させるケースはよくあります。こういう実装をするときこそ適切にコールバック順を知っておく必要があるため本章で理解を深めていきましょう。

    有限回数ループ設定したDOTween

    SetLoopsメソッドを使用してループするTweenで挙動を確認していきます。具体的には次のコードを実行します。

    void Start()  
    {
        var tween = transform.DOLocalMoveX (2f, 1f)  
            .OnStart (() => Debug.Log ("OnStart"))  
            .OnPlay (() => Debug.Log ("OnPlay"))  
            .OnKill (() => Debug.Log ("OnKill"))  
            .OnComplete (() => Debug.Log ("OnComplete"))  
            .OnPause (() => Debug.Log ("OnPause"))  
            .OnRewind (() => Debug.Log ("OnRewind"))  
            .OnStepComplete (() => Debug.Log ("OnStepComplete"))  
            .OnUpdate (() => Debug.LogWarning ("OnUpdate"))  
            .OnWaypointChange (x => Debug.Log ("OnWaypointChange" + x))  
            // 3回ループ設定  
            .SetLoops(3);  
    }
    

    結果は以下のようになります。

    1. OnStart
    2. OnPlay
    3. OnUpdate(毎フレーム実行)
    4. OnStepComplete(1回目)
    5. OnUpdate(毎フレーム実行)
    6. OnStepComplete(2回目)
    7. OnUpdate(毎フレーム実行)
    8. OnStepComplete(3回目)
    9. OnComplete
    10. OnKill

    ポイントはループ実行時に OnStepComplete が呼ばれる点です。逆にOnStepCompleteとOnUpdate以外呼ばれないことに注意してください。

    OnStepCompleteにLoopTypeは影響を受けない

    SetLoopsメソッドの第1引数でループ回数を設定し、第2引数にはLoopTypeを設定します。

    • LoopType.Restart
    • LoopType.Yoyo
    • LoopType.Incremental

    3種類のLoopTypeどれを設定しても コールバックには影響しない ということを覚えておきましょう。

    無限ループ設定のDOTween

    SetLoopsの引数に負の整数を設定して無限ループのTweenで挙動を確認していきます。

    void Start()  
    {
        var tween = transform.DOLocalMoveX (2f, 1f)  
            .OnStart (() => Debug.Log ("OnStart"))  
            .OnPlay (() => Debug.Log ("OnPlay"))  
            .OnKill (() => Debug.Log ("OnKill"))  
            .OnComplete (() => Debug.Log ("OnComplete"))  
            .OnPause (() => Debug.Log ("OnPause"))  
            .OnRewind (() => Debug.Log ("OnRewind"))  
            .OnStepComplete (() => Debug.Log ("OnStepComplete"))  
            .OnUpdate (() => Debug.LogWarning ("OnUpdate"))  
            .OnWaypointChange (x => Debug.Log ("OnWaypointChange" + x))  
            // 無限ループ設定  
            .SetLoops(-1);  
    }
    

    次のような結論になります。

    1. OnStart
    2. OnPlay
    3. OnUpdate(毎フレーム実行)
    4. OnStepComplete
    5. OnUpdate(毎フレーム実行)
    6. OnStepComplete
    7. OnUpdate(毎フレーム実行)...永遠に続く

    無限ループに設定しているため、OnStepCompleteとOnUpdateが永遠に繰り返されます。

    無限ループDOTween中にKill(true or false)

    次に無限ループDOTween中の中断処理を確認していきましょう。具体的には次のソースコードのようにKillメソッドを実行していきます。

    IEnumerator Start()  
    {
        var tween = transform.DOLocalMoveX (2f, 1f)  
            .OnStart (() => Debug.Log ("OnStart"))  
            .OnPlay (() => Debug.Log ("OnPlay"))  
            .OnKill (() => Debug.Log ("OnKill"))  
            .OnComplete (() => Debug.Log ("OnComplete"))  
            .OnPause (() => Debug.Log ("OnPause"))  
            .OnRewind (() => Debug.Log ("OnRewind"))  
            .OnStepComplete (() => Debug.Log ("OnStepComplete"))  
            .OnUpdate (() => Debug.LogWarning ("OnUpdate"))  
            .OnWaypointChange (x => Debug.Log ("OnWaypointChange" + x))  
            // 無限ループ設定  
            .SetLoops(-1);  
    
        yield return new WaitForSeconds(2f);  
    
        // 無限ループDOTweenを中断  
        tween.Kill(true); // or tween.Kill(false);  
    }
    

    次のような結果になりました。

    1. OnStart
    2. OnPlay
    3. OnUpdate(毎フレーム実行)
    4. OnStepComplete
    5. OnUpdate(毎フレーム実行)
    6. OnStepComplete
    7. OnUpdate(毎フレーム実行)
    8. OnKill

    ポイントはKillメソッドの引数にtrueを入れてもfalseを入れても OnComplete は呼ばれないということです。つまり 無限ループTweenではOnCompleteは実行されません。

    無限ループのDOTween中にCompleteは意味がない

    最後に無限ループDOTweenに対してTweenの完了メソッドCompleteを実行してみます。

    IEnumerator Start()  
    {
        var tween = transform.DOLocalMoveX (2f, 1f)  
            .OnStart (() => Debug.Log ("OnStart"))  
            .OnPlay (() => Debug.Log ("OnPlay"))  
            .OnKill (() => Debug.Log ("OnKill"))  
            .OnComplete (() => Debug.Log ("OnComplete"))  
            .OnPause (() => Debug.Log ("OnPause"))  
            .OnRewind (() => Debug.Log ("OnRewind"))  
            .OnStepComplete (() => Debug.Log ("OnStepComplete"))  
            .OnUpdate (() => Debug.LogWarning ("OnUpdate"))  
            .OnWaypointChange (x => Debug.Log ("OnWaypointChange" + x))  
            // 無限ループ設定  
            .SetLoops(-1);  
    
        yield return new WaitForSeconds(2f);  
        tween.Complete();  
    }
    
    1. OnStart
    2. OnPlay
    3. OnUpdate(毎フレーム実行)
    4. OnStepComplete
    5. OnUpdate(毎フレーム実行)
    6. OnStepComplete
    7. OnUpdate(毎フレーム実行)...永遠に続く

    ※Tweenは止まりません

    結論、無限ループのDOTweenに対してCompleteを実行してもTweenは止まりません。なぜなら無限ループのため完了という概念が存在しないからです。無限ループTweenを止めたい場合はKillを実行するということを覚えておきましょう。

    DOTweenコールバックのまとめ

    本記事ではDOTweenに実装されているコールバック関数について解説してきました。内容を簡単にまとめます。

    DOTweenコールバックのまとめ

    ①DOTweenの主要コールバックは8種類

    ②OnStartの呼び出しは1度きり

    ③DOTween終了時には必ずOnKill

    ④終了メソッドの引数によってOnCompleteは呼ばれない

    ⑤無限ループ設定時はOnCompleteは呼べない

    DOTweenに対してポーズや再開、ループといった設定をすることで呼ばれるコールバックと呼ばれないコールバックが出てきますし、呼び出し順も変わってきます。

    このあたりしっかりと理解して使わないと思わぬ落とし穴にハマり貴重な時間を無駄にしてしまう可能性があります。ぜひ本記事を参考にDOTweenのコールバックの処理順を改めてチェックしてみてください。

    DOTweenを使用することでUnity製のゲームにアニメーション、演出を簡単に追加することが可能です。

    例えば巻き戻し演出。

    SetLookAtを使った向きの制御。

    それぞれの記事を参考にチェックしてみてください。

    DOTweenの教科書
    【600冊以上販売】Unityのアニメーション用ライブラリのDOTweenを体系的に学べる教科書。11万文字の大ボリュー...
    詳しくはこちら
    DOTweenの教科書
    オススメ記事
    検証環境
    • Unity6000.0.32f1
    • DOTween v1.2.765