うにty生活

UnityChanを生活させたい

【感度・反転対応】マウスで視点移動したい #18

 

なぜか自分の中でVTuberのブームが一度も来ません

どうもラブヘイトです

 

今回は視点操作をマウスで実現したい

PCゲームでマウス視点操なんて当たり前体操なので実装できるようにしていきます

 

 

◆現状

今のUnityちゃんはボタンで視点を動かしています

 

tubakihimelovehate.hatenablog.com

 

しかし、これでは横軸にしかカメラを動かすことができません

縦軸も対応したいので、

 

 

何はともあれやってみよう

Quaternionとか出ませんように...笑

 

◆マウス視点移動イメージ

実現したい視点移動はもちろんこれですね笑

f:id:tubakihimeLoveHate:20190124213144g:plain



これは図にするとキャラクターを中心軸として動いている感じがします

f:id:tubakihimeLoveHate:20190124213232p:plain

図1



 

◆Unityで配置

図1の通りにUnityで配置するとこんな感じです

f:id:tubakihimeLoveHate:20190124213605p:plain

 

空のオブジェクトはこれから「Aimオブジェクト」と呼びます(エイムの意味が違うのは知ってますがわかりやすいので笑)

 

Aimオブジェクトはわかりやすさのため今はキューブにしてます

完成したらScriptだけの GameObjectに変えましょう!

 

 

◆上下視点移動に対応する

マウス視点移動にする前にまだ上下の視点移動が実装されていないので実装しました

前の記事で使った公式と同じようにして縦軸移動を試しましたが、結果ダメでした

 

思えば縦は360度回転する必要はなかったのです

なのでAimオブジェクトを上下させてそちらにLookAt()する方法に変えました

f:id:tubakihimeLoveHate:20190124214058g:plain



Aimオブジェクトにアタッチするコード

public class AimController : MonoBehaviour {

    public GameObject player;

    private Vector3 offset;
    private Vector3 setPosition;

    private Vector3 moveOffsetY;
 
    //半径
    private float r=5;
    //ラジアン
    private float deg = 0;
    
 
    void Start () {
 
        offset = transform.position + player.transform.position;
        moveOffsetY = new Vector3(0,0.3f,0);
 
    }
    
 
    void LateUpdate () {
     //横視点移動
        if(Input.GetKey(KeyCode.T)){
            deg += 3f;
        }else if(Input.GetKey(KeyCode.U)){
            deg -=3f;
        }
 
     //縦視点移動
        if(Input.GetKey(KeyCode.B)){
            offset += moveOffsetY;
        }

        if(Input.GetKey(KeyCode.N)){
            offset -= moveOffsetY;
        }
 
 
        setPosition.x = player.transform.position.x -r* Mathf.Cos(Mathf.Deg2Rad*deg);
        setPosition.y = player.transform.position.y - offset.y;
        setPosition.z = player.transform.position.z -r* Mathf.Sin(Mathf.Deg2Rad*deg);
        transform.position = setPosition;

 

カメラにアタッチするコード

上のコードとそんなに変わりません。計算部分を逆にするだけです

setPosition.x = player.transform.position.x +r* Mathf.Cos(Mathf.Deg2Rad*deg);
        setPosition.y = player.transform.position.y + offset.y;
        setPosition.z = player.transform.position.z +r* Mathf.Sin(Mathf.Deg2Rad*deg);
        transform.position = setPosition;
        transform.LookAt(aimObject.transform);

 

◆マウス視点移動対応 

縦の視点移動はoffsetに一定値をプラマイするだけ

どっちも縦と同じでよくね?って思うかもしれませんが、これだとUnityちゃんが画面外に出てしまう可能性があります(FPSなら大丈夫ですが)。なので横視点移動は今まで通りUnityちゃんの中心点から求めていきます

 

ここからマウスに対応していくには

Input.GetAxis関数でマウス移動した値を取得して計算します

最終的にこんな感じになりました↓

public class AimController : MonoBehaviour {

    public GameObject player;

    private Vector3 offset;
    private Vector3 setPosition;

 
  //ここをfloatに変えました
    private float moveOffsetY;

 
    //半径
    private float r=5;
    //ラジアン
    private float deg = 0;
  //横移動量
    float horizontal;
  //縦移動量
    float vertical;
 
 
    void Start () {
 
        offset = transform.position + player.transform.position;
 
    }
    
 
    void LateUpdate () {
     //*3fのところを変数にしたら感動設定できる
        horizontal = Input.GetAxis("Mouse X")*3f;
        vertical = Input.GetAxis("Mouse Y");
        
     //プラマイ変更で移動反転
        if(horizontal != 0){
            deg -= horizontal;
        }

        if(vertical != 0){
            moveOffsetY -= vertical;
        }
 
        setPosition.x = player.transform.position.x -r* Mathf.Cos(Mathf.Deg2Rad*deg);
        setPosition.y = player.transform.position.y - moveOffsetY;
        setPosition.z = player.transform.position.z -r* Mathf.Sin(Mathf.Deg2Rad*deg);
        transform.position = setPosition;
}
}
 

カメラのY軸は動かさないようにしました

public class CameraConrroller : MonoBehaviour {

    public GameObject player;
    public GameObject aimObject;

    private Vector3 offset;
    private Vector3 setPosition;
 
    //半径
    private float r=5;
    //ラジアン
    private float deg = 0;

    float horizontal;

    float vertical;

 
    void Start () {
        offset = transform.position - player.transform.position;
 
        transform.position += offset;
      }
    
 
    void LateUpdate () {
     //*3fのところを変数にしたら感動設定できる
     //*AimControllerと一緒の値にすること
        horizontal = Input.GetAxis("Mouse X")*3f;
        vertical = Input.GetAxis("Mouse Y");

        if(horizontal != 0){
            deg -= horizontal;
        }
 
        
        setPosition.x = player.transform.position.x +r* Mathf.Cos(Mathf.Deg2Rad*deg);
        setPosition.y = player.transform.position.y + offset.y;
        setPosition.z = player.transform.position.z +r* Mathf.Sin(Mathf.Deg2Rad*deg);
        transform.position = setPosition;
        transform.LookAt(aimObject.transform);
 
    }
}

 

まさかこんなに簡単なコードになるとは笑

しかも感度と反転にも対応!

では実際に動きを見ていきましょう

f:id:tubakihimeLoveHate:20190124215011g:plain

 

いい感じだぁあああ!

感度を調節すればもっと良くなると思います

 

これで最後に「Aimオブジェクト」をAimCntrollerスクリプトだけのオブジェクトにします

f:id:tubakihimeLoveHate:20190124225100g:plain

 

◆比較

fortniteのキャラクターは視点の方に体も向いています

これはUnityちゃんにもAimオブジェクトの方へLookAt()してもらえば実現しますが、問題は縦です笑

この状態でAimオブジェクトを上にあげたら・・・

面白いことになるのは目に見えていますね笑

 

fortniteは縦視点移動の時は首から上を動かしています

これは今すぐにはできないので今回はキャラクターの向きについてはまた後日改めて投稿しますのでよろしくお願いします

 

◆おまけ

せっかく視点移動をPCゲームみたいにしたのに、移動方法がいまだに十字キーだったので変更しました

void FixedUpdate()
{

/*
float h = Input.GetAxis("Horizontal");
float v = Input.GetAxis("Vertical");
*/
if(Input.GetKey(KeyCode.W))v=1;
//if(Input.GetKey(KeyCode.S))v=-1;
if(Input.GetKey(KeyCode.A))h=-1;
if(Input.GetKey(KeyCode.D))h=1;
 
Vector3 velocity = new Vector3(0, 0, v);
 

    // キャラクターのローカル空間での方向に変換
    velocity = transform.TransformDirection(velocity);

float speedCache = speed *pulusSpeed* Time.fixedDeltaTime;

    // キャラクターの移動
    transform.localPosition += velocity * speedCache;

 
// キャラクターの回転
    transform.Rotate(0, h * rotateSpeed * Time.fixedDeltaTime, 0);
 

ダッシュを「Eキー」にしたかったのですが、W,E,Dと隣接しているキーを3つ以上押すと3つ目は反応しないみたいです

 

今日はここまで