【5分で作る!】 フェードインをAnimationを使ってあっさり実装してみよう!
みなさん、お疲れ様です。Unity初心者のユウです。 仕事が忙しくて全く更新できてませんでした。家に帰ると力尽きてしまうですよね。
さて、ウィザードリィもどきの下書きも少し書いているのですが、今回は技術ブログのマネごとをするためになにかをやる方法的なことを書きたかったので この間自分でも作っていたフェードイン、フェードアウト実装方法をあえて紹介したいと思います。
Unity初心者がフェード処理と聞くとややこしく感じられるかもしれませんが
今回、スクリプトは2行程度しか書きません!! とっても簡単ですよ!
- フェードイン作りてぇ…!
- ヒエラルキーにImageを設置する
- Animationでフェードイン、フェードアウトを作ろう
- ちょこっとスクリプトを書こう!
- AnimationにEventを追加しよう
- 完成!
フェードイン作りてぇ…!
Unityでゲームをシコシコと作っていると、シーンの切り替えを作ることが増えてきますよね。そういうシーンを切り替えるときってたぶん最初の状態だとぶつ切り状態になってしまっていると思います。
少しでもそれっぽくみせるためにフェードインやフェードアウトを使うことが多いのですが、updateやコルーチンでcolorのalphaを変動させたりしないといけないなど、ちょっとややこしいので敬遠してしまう方もいらっしゃるかもしれません。
そこで、今回は「Animation」を利用した雑なフェードイン処理を作っていきたいと思います。 今回はフェードインを例に作っていきます。完成イメージはこんな感じ
今回はズボラなので、Scene開始時、最初に実行されることを想定しています。任意のタイミングで呼びたい場合は少し改良する必要があります。
ヒエラルキーにImageを設置する
フェードイン、フェードアウトを実装する方法としてよく使われるのが真っ黒な画像を使ってその透明度をいじる。というものがあります。 今回もそれを使っていきたいと思いますので、まずは黒塗りのマスク画像を作るためにUIのImageを作っていきましょう!
さて、フェードインやフェードアウトって最前面で実行する必要があります。なのでまずは「Canvas」をクリックして「Sort Order」を大きい数字にしておきましょう。今回は「999」としています。
続いて、「Image」をクリックして各種設定を変更していきます。画面全体を覆いたいのでとりあえず「Width」と「Height」を大きくしておきます。スケールをいじっても構いません。 今回は黒塗りにするので「Color」を「Black」にしておきます。
さぁこれでフェードイン、フェードアウトの下準備が整いました。続いて作っていきましょう
Animationでフェードイン、フェードアウトを作ろう
本来ならこのあとスクリプトを組んでフェードイン処理やフェードアウト処理を作っていくのですが、今回はズボラな方法としてAnimationで実装します! 「Image」を選択したまま、「Window -> Animation -> Animation」をクリックしましょう。
まだ何もないので「Create」をクリックして作りましょう! Animationの保存先を聞かれるのでほどよき所に好きな名前で保存します。「Fade」とでもしておきましょうか。
続いて、Animationを追加していきたいと思います。 「Add Property」をクリックしましょう!
「Image」から、「Color」の+ボタンをクリックして追加します。
左側の「Image.Color」が閉じている場合は左の「▼」ボタンをクリックして展開します。 続いてタイムラインの「1:00」にあるキーフレームをクリックして選択(青色の状態)にします!
黒塗りから透明になりたいので、1秒後には透明になっているのが理想です。これを実現するためには「Color」の情報の中にある「alpha(透明度)」をいじってあげる必要があります。なので、現在選択している「1:00」の「Color.a」をクリックして「0」を入力します。
この段階で左上部の「▶」ボタンをクリックするとAnimationの確認ができます。設定がうまくいっていれば黒い画像がだんだん透明になっていくのが確認できるかと思います。
さて、この段階だと再生するとループしてしまって目がチカチカしてしまいます。フェードインなのですから1回だけ実行してほしいですよね。 Assetから、さきほど作ったAnimationの「Fade」をクリックして選択し「Loop Time」のチェックを外します
処理とは関係ないですが、ちょっと分かりづらいので、ここで「Canvas」の名前を「FadeIn」に変えてみました。
これでフェードインはほぼ完成です!! お疲れ様でした! と言いたいところですが、このままだと透明になったフェードイン画像が最前面に残ったままでだめです。仕上げに移っていきましょう!
ちょこっとスクリプトを書こう!
汎用性を考えるとちゃんと作らないといけませんが、今回の主題はあくまでもずぼらに作るフェードイン処理風味です。 言ってしまえば自分で食べるために冷蔵庫の残り物を鍋にぶちこんで卵でとじて食べるぐらいの雑さで良いのです。
現段階での問題点は下記2点が気になります。
- Scene画面で黒い画像が邪魔すぎる
- フェードインしたあと透明になってるだけで画像が存在していて邪魔
なのでこの2点に対してアプローチをしていきましょう。
画像が邪魔なら非表示にすればいいじゃない
マリー・アントワネット的解決方法です。そうです、とりあえず非表示にしとけばいいよねっていう考え方です。 さきほどの「FadeIn」キャンバスの「Image」をクリックします。「Image」のチェックを外して非有効化しておきます。こうするとScene上では表示されません。 ただしGameObjectとしては存在しているのでスクリプトで処理とか、Findで見つけたりとかはできます。
簡単なことですが、これで1番目の問題はとりあえず解決しました! 次だ次!
画像が邪魔なら非表示にすればいいじゃない
タイトルのコピペミスではありません。 結局、これなんです。いらないなら非表示にするかデストロイすればいい。強さこそこの世紀末の正義よ…!
ついでにいうとさっき非表示にしちゃってるので表示するためのスクリプトを書く必要があるのでそれもあわせてやってしまいましょう。
「Asset」から「Create -> C# Script」をクリックして新しいスクリプトを作成します。名前は何でも良いですが、「FadeInController 」とでも名付けてみましょう。作成できたらスクリプトを開きましょう。
まず、有効化するためのスクリプトを書きます。今回はタイミングを考慮せず「Start」内に書いてしまいます。
つまりこのFadeInのキャンバスを設置しておけば自動的にそのScene開始時にフェードイン処理が行われるということです。
ちなみに、UIをいじくるので スクリプトにusing UnityEngine.UI;
を書いておいてください。
void Start() { GetComponent<Image>().enabled = true; }
さきほど非有効化していた「Canvas」をスクリプト側から有効にしています。 続いて、フェードが終わったあとの処理を書きたいのですがどこに書くかが問題です。今回は折角Animationを使っているのでオブジェクトの消去に関しても連携してみましょう。さきにコードを記述します。新しいメソッドを作ります。
// フェードイン終了後の処理 public void EndFadeInAnimation() { Destroy(this.gameObject); }
非表示でも良いのですが、デストロイでも良いです。お好みにあわせてどうぞ。 フェードイン用のPrefabとして考えるなら親オブジェクトのキャンバスごと削除してしまうのもいいかもしれません。あるいはAnimationをtriggerで再生するようにして使いまわすなら非表示とかにすると良いですね。
ここまでのソースコードはこんな感じです。
using System.Collections; using System.Collections.Generic; using UnityEngine; using UnityEngine.UI; public class FadeInController : MonoBehaviour { // Start is called before the first frame update void Start() { GetComponent<Image>().enabled = true; } // Update is called once per frame void Update() { } // フェードイン終了後の処理 public void EndFadeInAnimation() { Destroy(this.gameObject); } }
作成したスクリプトを「Image」にアタッチしておきましょう!
AnimationにEventを追加しよう
さて、ここでAnimationに戻ります。「FadeIn」キャンバスの「Image」をクリックして「Window -> Animation -> Animation」をクリックしましょう。
さきほど作ったAnimationが表示されます。「1:00」でアニメーションが終わるので、その後ろあたりのタイムラインをクリックして選択します。 「Add event」をクリックしてイベントを追加します。
このイベントではアニメーションがアタッチされているオブジェクトのスクリプトのメソッドを指定してあげることができます。なのでさっき作ったメソッドを呼び出してやりましょう。 今回はアニメーション終了後のイベントなので、アニメが終わったらメッソドが呼ばれるイメージです。
EndFadeInAnimation()
と、さきほど作ったメソッドを指定してあげます。
これで完成です!
完成!
無事、フェードインを作ることができました。今回はフェードインでしたが、逆に透明な状態からはじめて透明度を1にしていく逆の処理を書けばフェードアウトを実装することもできます。
また今回は必ず初回に実行されてしまい任意のタイミングで使うことができません。これを解決するには、Animatorを使ってAnimation再生タイミングを調整するか、そもそもこのフェードインオブジェクトのアクティブタイミングを変えるなどの方法が考えられそうです。
Update内にいちいちフェードインをじわじわやっていく処理を書かずにAnimationだけで実装できるので、まず初心者が見よう見まねでフェード処理を作りたいときは良いのではないでしょうか。 今回は先にオブジェクトを作っていますが、スクリプト側からオブジェクトを作るようにすればさらに汎用性が高まりますので次のステップとして良いかもしれませんね!