feat(PlayerCamera):完成玩家的第一人称相机
This commit is contained in:
101
Assets/Script/Player/PlayerCameraController.cs
Normal file
101
Assets/Script/Player/PlayerCameraController.cs
Normal file
@@ -0,0 +1,101 @@
|
||||
using Core;
|
||||
using UnityEngine;
|
||||
|
||||
namespace Player
|
||||
{
|
||||
/// <summary>
|
||||
/// 玩家第一人称相机控制器
|
||||
/// 挂到相机或相机父物体,playerBody 指向角色的根 Transform(用于左右旋转)
|
||||
/// </summary>
|
||||
/// TODO:使用InputManager替换掉Input.GetAxis
|
||||
public class PlayerCameraController : MonoBehaviour
|
||||
{
|
||||
[Header("References")]
|
||||
[Tooltip("角色根 Transform,用于水平旋转(yaw)")]
|
||||
public Transform playerBody;
|
||||
[Tooltip("如果相机不是挂载在同一物体上,可以指定相机 Transform(可选)")]
|
||||
public Transform cameraTransform;
|
||||
|
||||
[Header("Sensitivity & Invert")]
|
||||
[Tooltip("鼠标灵敏度")]
|
||||
[Range(0.01f, 1f)]
|
||||
public float mouseSensitivity = 0.2f;
|
||||
|
||||
[Tooltip("反转垂直轴")]
|
||||
public bool invertY = false;
|
||||
|
||||
[Header("Vertical Limits")]
|
||||
[Tooltip("向上最大仰角(度)")]
|
||||
public float maxUpAngle = 60f;
|
||||
[Tooltip("向下最大俯角(度)")]
|
||||
public float maxDownAngle = 60f;
|
||||
|
||||
[Header("Smoothing")]
|
||||
public bool enableSmoothing = false;
|
||||
[Tooltip("旋转平滑时间(秒)")]
|
||||
public float smoothTime = 0.05f;
|
||||
|
||||
// internal state
|
||||
private float xRotation = 0f; // 垂直角(pitch)
|
||||
private float yaw = 0f; // 水平角(yaw)
|
||||
private float smoothVelocityPitch = 0f;
|
||||
private float smoothVelocityYaw = 0f;
|
||||
|
||||
void Start()
|
||||
{
|
||||
if (cameraTransform == null)
|
||||
cameraTransform = transform;
|
||||
|
||||
// 初始化当前角度以避免跳变
|
||||
Vector3 euler = cameraTransform.localEulerAngles;
|
||||
xRotation = NormalizeAngle(euler.x);
|
||||
yaw = NormalizeAngle(playerBody ? playerBody.eulerAngles.y : transform.eulerAngles.y);
|
||||
|
||||
}
|
||||
|
||||
void Update()
|
||||
{
|
||||
Vector2 mouse = InputManager.Instance.Look;
|
||||
|
||||
// ✅ 不要乘 Time.deltaTime,因为 Look 已经是每帧的增量
|
||||
float mouseX = mouse.x * mouseSensitivity;
|
||||
float mouseY = mouse.y * mouseSensitivity;
|
||||
|
||||
float invert = invertY ? 1f : -1f;
|
||||
|
||||
yaw += mouseX;
|
||||
xRotation += mouseY * invert;
|
||||
|
||||
// 限制垂直角度
|
||||
xRotation = Mathf.Clamp(xRotation, -maxDownAngle, maxUpAngle);
|
||||
|
||||
if (enableSmoothing)
|
||||
{
|
||||
float smoothPitch = Mathf.SmoothDampAngle(cameraTransform.localEulerAngles.x, xRotation, ref smoothVelocityPitch, smoothTime);
|
||||
float smoothYaw = Mathf.SmoothDampAngle(playerBody ? playerBody.eulerAngles.y : transform.eulerAngles.y, yaw, ref smoothVelocityYaw, smoothTime);
|
||||
|
||||
cameraTransform.localRotation = Quaternion.Euler(smoothPitch, 0f, 0f);
|
||||
if (playerBody)
|
||||
playerBody.rotation = Quaternion.Euler(0f, smoothYaw, 0f);
|
||||
else
|
||||
transform.rotation = Quaternion.Euler(0f, smoothYaw, 0f);
|
||||
}
|
||||
else
|
||||
{
|
||||
cameraTransform.localRotation = Quaternion.Euler(xRotation, 0f, 0f);
|
||||
if (playerBody)
|
||||
playerBody.rotation = Quaternion.Euler(0f, yaw, 0f);
|
||||
else
|
||||
transform.rotation = Quaternion.Euler(0f, yaw, 0f);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// 将角度规范到 [-180,180] 范围,避免插值跳变
|
||||
private float NormalizeAngle(float angle)
|
||||
{
|
||||
angle = (angle + 180f) % 360f - 180f;
|
||||
return angle;
|
||||
}
|
||||
}
|
||||
}
|
3
Assets/Script/Player/PlayerCameraController.cs.meta
Normal file
3
Assets/Script/Player/PlayerCameraController.cs.meta
Normal file
@@ -0,0 +1,3 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 2525a4f94ebe4e789ed375bd17d6a1a7
|
||||
timeCreated: 1760424747
|
Reference in New Issue
Block a user