第一人称相机视角控制

1、目录结构
在这里插入图片描述
2、Player添加第三人称控制组件 character controller
3、脚本如下

using UnityEngine;
using System.Collections;
using System;
using DG.Tweening;

public class FirstViewControl : MonoBehaviour
{
public enum FirstViewControlState
{
noUse,//不使用
playerControl,//第一人称控制
playerAnim,//第一人动画
}

public Transform characterTrans, camTrans;


public static FirstViewControl instance { set { } get { return _instance; } }
private static FirstViewControl _instance;
void Awake()
{
    _instance = this;
}

void Start()
{
    if (characterTrans == null)
        characterTrans = this.gameObject.transform;
    if (camTrans == null)
        camTrans = this.gameObject.transform.Find("Main Camera").transform;

    IniQuaternion();
}

void Update()
{
    JueSeKongZhi();
}
public FirstViewControlState playerState = FirstViewControlState.playerControl;
[HideInInspector]
public bool isCanSimpleMove = true, isCanRotate = true, isCanUpDown = true, isCanScrollView = true;
[HideInInspector]
public bool isTextInput;

void JueSeKongZhi()
{
    if (playerState == FirstViewControlState.playerControl)
    {
        if (isCanSimpleMove && !isTextInput)
            SimpleMove();
        if (isCanRotate)
            RotateCamera();
        if (isCanUpDown)
            CamUpDown();
        if (isCanScrollView)
            CamViewScale();

    }
}

#region  人物移动
[Header("人物移动")]
Vector3 movedir;
public float moveSpeed = 0.1f;

/// <summary>
/// 人物移动
/// </summary>
public void SimpleMove()
{
    float h = Input.GetAxis("Horizontal");
    float v = Input.GetAxis("Vertical");
    if (h != 0 || v != 0)
    {
        float va = camTrans.gameObject.GetComponent<Camera>().fieldOfView;
        movedir = transform.TransformDirection(new Vector3(h, 0, v).normalized * moveSpeed * va * Time.deltaTime);
        characterTrans.GetComponent<CharacterController>().Move(movedir);
    }


}
#endregion

#region 相机旋转
[Header("相机旋转")]
private float XSensitivity = 3f;
private float YSensitivity = 3f;
private Quaternion m_CharacterTargetRot;
private Quaternion m_CameraTargetRot;
private bool clampVerticalRotation = true;
private bool smooth = true;
private float smoothTime = 5f;

public void IniQuaternion()
{
    m_CharacterTargetRot = characterTrans.localRotation;
    m_CameraTargetRot = camTrans.localRotation;
}
/// <summary>
/// 相机旋转
/// </summary>
public void RotateCamera()
{
    if (Input.GetMouseButton(0))
    {
        float yRot = Input.GetAxis("Mouse X") * XSensitivity;
        float xRot = Input.GetAxis("Mouse Y") * YSensitivity;

        m_CharacterTargetRot *= Quaternion.Euler(0f, yRot, 0f);
        m_CameraTargetRot *= Quaternion.Euler(-xRot, 0f, 0f);

        if (clampVerticalRotation)
            m_CameraTargetRot = ClampRotationAroundXAxis(m_CameraTargetRot);
        if (smooth)
        {
            characterTrans.localRotation = Quaternion.Slerp(characterTrans.localRotation, m_CharacterTargetRot,
                smoothTime * Time.deltaTime);
            camTrans.localRotation = Quaternion.Slerp(camTrans.localRotation, m_CameraTargetRot,
                smoothTime * Time.deltaTime);

        }
        else
        {
            characterTrans.localRotation = m_CharacterTargetRot;
            camTrans.localRotation = m_CameraTargetRot;
        }
    }
    if (Input.GetMouseButtonUp(0))
    {
        if (smooth)
        {
            m_CharacterTargetRot = characterTrans.localRotation;
            m_CameraTargetRot = camTrans.localRotation;
        }
    }

}

private float MinimumX = -60F;
private float MaximumX = 60F;
Quaternion ClampRotationAroundXAxis(Quaternion q)
{
    q.x /= q.w;
    q.y /= q.w;
    q.z /= q.w;
    q.w = 1.0f;

    float angleX = 2.0f * Mathf.Rad2Deg * Mathf.Atan(q.x);

    angleX = Mathf.Clamp(angleX, MinimumX, MaximumX);

    q.x = Mathf.Tan(0.5f * Mathf.Deg2Rad * angleX);

    return q;
}
#endregion

#region 相机上下移动
[Header("相机上下移动")]
private int dirNum = 0;//判断中建按下停止不动时 是向下还是向上移动
private float camUpDownSpeed = 0.8f;//相机上下速度

private float shangXia;

public float camHeightMax = 0.5f;//相机最高高度
public float camHeightMin = -0.5f;//相机最低高度


/// <summary>
/// 相机上下移动
/// </summary>
public void CamUpDown()
{
    if (Input.GetMouseButton(2))//?м?????
    {
        shangXia = shangXia + 0.5f * Input.GetAxis("Mouse Y");
        shangXia = Mathf.Clamp(shangXia, -5.3f, 5.3f);

        camTrans.localPosition = new Vector3(camTrans.localPosition.x, Mathf.Clamp(camTrans.localPosition.y, camHeightMin, camHeightMax), camTrans.localPosition.z);

        camTrans.Translate(0, shangXia * 0.01f, 0,Space.World);
    }
    else if (Input.GetMouseButtonUp(2))
    {
        shangXia = 0;
    }
}
#endregion

#region  相机view值变化
//[Header("相机视角值变化")]
private float camViewSpeed = -50;//相机view变化速度
public void CamViewScale()
{

    float h = Input.GetAxis("Mouse ScrollWheel");
    if (h != 0)
    {
        float value = Mathf.Clamp(camTrans.GetComponent<Camera>().fieldOfView + camViewSpeed * h, 20, 60);
        DOTween.To(() => camTrans.GetComponent<Camera>().fieldOfView, x => camTrans.GetComponent<Camera>().fieldOfView = x, value, 0.2f).SetEase(Ease.Linear);
        camUpDownSpeed = (camTrans.GetComponent<Camera>().fieldOfView - 20) * 0.7f / 40 + 0.05f;
    }
}


#endregion

//摄像机动画
public void MoveToDestination(Vector3 pos, Vector3 ros, Vector3 cameraRos, float hight, float delay, float time, float View = 60)
{
    playerState = FirstViewControlState.playerAnim;
    if (camTrans.GetComponent<Camera>().fieldOfView < 59 && Mathf.Abs(camTrans.GetComponent<Camera>().fieldOfView - View) > 5)
    {
        DOTween.To(() => camTrans.GetComponent<Camera>().fieldOfView, x => camTrans.GetComponent<Camera>().fieldOfView = x, 60, 1f).SetDelay(delay).SetEase(Ease.InOutQuad);
        delay += 1;
    }

    characterTrans.DOLocalMove(pos, time).SetRelative(false).SetDelay(delay).SetEase(Ease.InOutQuad);
    characterTrans.DOLocalRotate(ros, time).SetRelative(false).SetDelay(delay).SetEase(Ease.InOutQuad);

    camTrans.GetComponent<Camera>().transform.DOLocalRotate(cameraRos, time).SetRelative(false).SetDelay(delay).SetEase(Ease.InOutQuad);
    camTrans.transform.DOLocalMoveY(hight, time).SetDelay(delay).SetEase(Ease.InOutQuad);
    DOTween.To(() => camTrans.GetComponent<Camera>().fieldOfView, x => camTrans.GetComponent<Camera>().fieldOfView = x, View, time).SetRelative(false).SetDelay(delay).SetEase(Ease.Linear).OnComplete(() =>
    {
        if (smooth)
            IniQuaternion();
        playerState = FirstViewControlState.playerControl;
    });
}


public Tweener MoveToDestination(Vector3 playerPos, Vector3 playerRot, Vector3 camPos, Vector3 _camRot, float time, float detime, float fieldvalue)
{
    playerState = FirstViewControlState.playerAnim;
    //CommandManager.instance.ExecuteCommand(this, false, "playermove", playerPos, playerRot, camPos, _camRot, time, detime, fieldvalue);
    if (camTrans.GetComponent<Camera>().fieldOfView < 59 && Mathf.Abs(camTrans.GetComponent<Camera>().fieldOfView - fieldvalue) > 5)
    {
        DOTween.To(() => camTrans.GetComponent<Camera>().fieldOfView, x => camTrans.GetComponent<Camera>().fieldOfView = x, 60, 1f).SetDelay(detime).SetEase(Ease.InOutQuad);
        detime += 1;
    }
    Tweener t = default(Tweener);
    this.transform.DOLocalMove(playerPos, time).SetRelative(false).SetDelay(detime).SetEase(Ease.InOutQuad);
    this.transform.DOLocalRotate(playerRot, time).SetRelative(false).SetDelay(detime).SetEase(Ease.InOutQuad);
    Camera.main.transform.DOLocalMove(camPos, time).SetRelative(false).SetDelay(detime).SetEase(Ease.InOutQuad);
    t = Camera.main.transform.DOLocalRotate(_camRot, time).SetRelative(false).SetDelay(detime).SetEase(Ease.InOutQuad);

    Tweener tt = DOTween.To(() => Camera.main.fieldOfView, x => Camera.main.fieldOfView = x, fieldvalue, time).SetRelative(false).SetDelay(detime).SetEase(Ease.InOutQuad);
    if (smooth)
    {
        t.OnComplete(() =>
           IniQuaternion());
        playerState = FirstViewControlState.playerControl;
    }
    return tt;
}

}

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值