Cinemachineのバーチャルカメラの切り替えを検知して、プレイヤーの動きを止めたり、テキストを非表示にしました。
スターターアセットのPlaygroundシーンを使います。
ターゲット
シーンにCGTraderでダウンロードしたモアイ像を置きました。
モアイ像の子としてバーチャルカメラのターゲットにする空のゲームオブジェクトを追加します。
バーチャルカメラ
新規バーチャルカメラを追加して、LookAtにこのゲームオブジェクトをアタッチします。
Bodyは「Do nothing」、Aimは「Hard Look At」にしました。
バーチャルカメラがターゲットを画面の中央に維持するようになるので、優先度を上げてゲームビューを見ながら位置を調節します。
バーチャルカメラの切り替え
スクリプトで優先度を変えることでバーチャルカメラを切り替えます。プレイヤーの三人称視点カメラとモアイのカメラをスクリプトにアタッチします。
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using Cinemachine;
public class MoaiCameraTest : MonoBehaviour
{
[SerializeField] CinemachineVirtualCameraBase tpsCamera;
[SerializeField] CinemachineVirtualCameraBase moaiCamera;
public bool CanBlendMoai { get; set; }
// Start is called before the first frame update
void Start()
{
tpsCamera.Priority = 10;
moaiCamera.Priority = 9;
}
// Update is called once per frame
void Update()
{
if(Input.GetKeyDown(KeyCode.F) && CanBlendMoai)
{
tpsCamera.Priority = 10;
moaiCamera.Priority = 11;
}
if(Input.GetKeyUp(KeyCode.F))
{
tpsCamera.Priority = 10;
moaiCamera.Priority = 9;
}
}
}
メインカメラのCinemachineBrainコンポーネントでブレンドのスタイルや時間を指定できます。少し時間を短くしました。
On Camera Live
モアイを表示している間も、キー入力などでプレイヤーが動きます。
バーチャルカメラのOn Camera Liveで、バーチャルカメラの切り替えを検知して、プレイヤーを停止します。
プレイヤーにスクリプトを付けて停止できるようにします。
using UnityEngine;
using StarterAssets;
public class TestPlayer1 : MonoBehaviour
{
ThirdPersonController tps;
private void Awake()
{
tps = GetComponent<ThirdPersonController>();
}
public bool IsPaused { get => !tps.enabled; set => tps.enabled = !value; }
}
2つのバーチャルカメラのOn Camera Liveイベントにプレイヤーを停止するプロパティを設定します。
ブレンド中に壁を突き抜ける
ブレンド中にバーチャルカメラが壁を突き抜けてしまいます。
Cinemachineコライダーでは解決しないので、モアイカメラへ切り替えられる範囲を限定してみました。シーンにBoxコライダーを追加してIs Triggerをオンにします。
プレイヤーがこのトリガーの中にいるときにだけモアイカメラとブレンドできるようにします。またカメラを切り替えられることがわかるようにテキスト表示します。
シーンにCanvasとテキストを追加して、Canvasにスクリプトを付けました。
using System.Collections;
using UnityEngine;
using UnityEngine.UI;
public class MoaiCameraCanvas : MonoBehaviour
{
[SerializeField] Text moaiText;
// モアイカメラがライブになったとき
public void OnMoaiCameraLive()
{
// テキストを非表示にする
StopCoroutine("DelayAndShowText");
moaiText.gameObject.SetActive(false);
}
// TPSカメラがライブになったとき
public void OnTPSCameraLive()
{
// 遅延後テキストを表示する
StartCoroutine("DelayAndShowText");
}
bool canBlendMoai;
// モアイカメラとブレンドできる
public bool CanBlendMoai { get=> canBlendMoai;
set
{
// 値が変わったとき
if(canBlendMoai != value)
{
// テキストを表示/非表示
moaiText.gameObject.SetActive(value);
}
canBlendMoai = value;
}
}
// テキストを表示するコルーチン
IEnumerator DelayAndShowText()
{
yield return new WaitForSeconds(0.75f);
// モアイカメラとブレンドできるときはテキストを表示
moaiText.gameObject.SetActive(canBlendMoai);
}
}
テキストはスクリプトにアタッチして、非アクティブにしておきました。
トリガーにスクリプトを付けてプレイヤーのエンターとイグジットを、テキストを表示するスクリプトと、ブレンドを開始/終了するスクリプトに教えます。
using UnityEngine;
public class MoaiCameraTrigger : MonoBehaviour
{
[SerializeField] MoaiCameraTest test;
[SerializeField] MoaiCameraCanvas canvas;
// プレイヤーがエンター
private void OnTriggerEnter(Collider other)
{
if(other.tag != "Player") return;
test.CanBlendMoai = true;
canvas.CanBlendMoai = true;
}
// プレイヤーがイグジット
private void OnTriggerExit(Collider other)
{
if(other.tag != "Player") return;
test.CanBlendMoai = false;
canvas.CanBlendMoai = false;
}
}
テキストを非表示
モアイカメラがLiveのときはテキストを非表示にします。これにはプレイヤーの停止と同様に、2つのバーチャルカメラのOn Camera LiveにCanvasのスクリプトをアタッチします。
// Canvasのスクリプト
// モアイカメラがライブになったとき
public void OnMoaiCameraLive()
{
// テキストを非表示にする
StopCoroutine("DelayAndShowText");
moaiText.gameObject.SetActive(false);
}
// TPSカメラがライブになったとき
public void OnTPSCameraLive()
{
// 遅延後テキストを表示する
StartCoroutine("DelayAndShowText");
}
バーチャルカメラのブレンドを開始/終了するスクリプトにアタッチしても良いかもしれません。
バーチャルカメラのブレンドが開始したときにテキストが表示されるので、コルーチンを使ってテキストの表示前に少し遅延を入れています。
// Canvasのスクリプト
IEnumerator DelayAndShowText()
{
yield return new WaitForSeconds(0.75f);
// モアイカメラとブレンドできるときはテキストを表示
moaiText.gameObject.SetActive(canBlendMoai);
}
ブレンド中に再度キーを押したときには、コルーチンを停止します。
public void OnMoaiCameraLive()
{
StopCoroutine("DelayAndShowText");
// ...
}
また、遅延後にプレイヤーがすでにトリガーの外にいた場合は、テキストを表示しないようにしています。
実行
Cinemachine Camera Events
Cinemachine 3.0.0では、ブレンドが終了したときに発生するイベントなどを利用できるCinemachine Camera Eventsコンポーネントが追加されるようです。
https://docs.unity3d.com/Packages/com.unity.cinemachine@3.0/manual/CinemachineCameraEvents.html