暑い
この暑さの中、マスクを着けて歩くなんて狂気の沙汰だと思う皆さんこんにちは。6月ってこんなに暑かったかな?
去年が冷夏だった分、その反動でこの夏は猛暑になりそうで凄く嫌。
Dotweenによる回転
例えば歯車のようなオブジェクトを回転させたい場合、DotweenだとDORotateを使います。
そしてこの回転を延々と続けたい場合はLoopオプションに「-1」を設定します。
GearObj.transform.DOLocalRotate(new Vector3(0.0f, 0.0f, 360.0f), 2.0f) .SetRelative(true) .SetLoops(-1);
まぁ、このぐらいの動作なら簡単に実装できるのですが、これを「1秒待った後に10度回転する」動作を繰り返す、という処理を実装しようとした場合ちょっと頭を悩ませます、ってか、結構悩みました。今回はそのお話。
Delayの設定
当初は「1秒待った後に」とあるので、Delayオプションをつければ良かろう、と単純に考えていたのです
GearObj.transform.DOLocalRotate(new Vector3(0.0f, 0.0f, 10.0f), 0.7f) .SetRelative(true) .SetDelay(1.0f) .SetLoops(-1);
実際に動かしてみると
ん~・・普通に回転しとる
DORotateのDelayオプションはあくまで「回転動作開始の遅延」設定であるため、遅延が発生するのは最初の一回だけですのようです。Loopオプションで繰り返されるのは回転動作の部分のみ、なるほどね。
なので次はSequenceを使うことにしました。Sequenceに上のDORotateをAppendして、SequenceのLoopオプションに「-1」を設定。
Sequence GearSeq = DOTween.Sequence(); GearSeq.Append( GearObj.transform.DOLocalRotate(new Vector3(0.0f, 0.0f, 10.0f), 0.7f) .SetRelative(true) .SetDelay(1.0f) );
GearSeq.SetLoops(-1);
これでSequenceを繰り返す=「最初の遅延動作」+「回転動作」を繰り返す、となるはずなので「1秒待った後に10度回転する」動作が繰り返されるはずです。
・・・なんだこれ?・・・
Loopの設定
なるほど、Sequenceを繰り返す、ということは指定のTweenを最初から実行する、となりますが、DORotateを最初から実行するということは「初期角度から指定角度まで回転する」という動作を繰り返すことになります。これでは上の動画みたいに壊れたレコードみたいな動作となるのは当然です。なるほど、なるほど
Loopオプションは第一引数でループ回数を指定出来ますが、第二引数にループの挙動も指定することができます。
- Restart: 挙動が終了した時に値を始点に戻し、再度実行する
- Yoyo: ヨーヨーのように行き戻りを繰り返す
- Incremental: 挙動が終了した時に差分を endValue に追加しつつ再度Tweenを実行する
今回の場合はLoopTypeにIncrementalを指定する必要があったみたいです。
GearSeq.SetLoops(-1, LoopType.Incremental);
さっそく追加して実行
・・・なんだこれ?(二度目)・・・
暫定対応
よく見ると回転動作の最終位置は加算されているようで、じわじわ回転しているのはわかります。が、何故か動作開始位置が前回動作時のendValueとなっていないようで先ほどの動作と大して変わらない挙動となってしまいます。
色々と調べましたがお手上げとなってしまったので暫定的な対応としてDelayオプションによる遅延動作をあきらめ、Sequenceに遅延時間分ダミーオブジェクトを動作させるTweenを追加、これを繰り返すことにしました。
左の歯車がダミーオブジェクト
本命オブジェクトのDORotate前に左のダミーオブジェクトを遅延時間分回転させています。
GearSeq = DOTween.Sequence(); GearSeq.Append( DummyObj.transform.DOLocalRotate(new Vector3(0.0f, 0.0f, 360.0f), 1.0f) .SetRelative(true) ); GearSeq.Append( GearObj.transform.DOLocalRotate(new Vector3(0.0f, 0.0f, 10.0f), 0.7f) .SetRelative(true) ); GearSeq.SetLoops(-1, LoopType.Incremental);
一応これで想定する動作を実現することができましたが、何かほかに良い方法があればだれか教えてください。
ちなみに、どうしてこんな動作を作る必要があったのかと言えば、現在作成中のゲーム内で使用するためです。
こんな場面で使っています。