移除错误的玩家预制体
This commit is contained in:
@@ -1,219 +0,0 @@
|
||||
using UnityEngine;
|
||||
using UnityEngine.InputSystem;
|
||||
|
||||
/// <summary>
|
||||
/// Capsule player: camera-relative movement, jump, gravity and mouse look.
|
||||
/// Input comes from the project asset Assets/InputSystem_Actions.inputactions
|
||||
/// ("Player" map: Move / Jump / Sprint).
|
||||
/// </summary>
|
||||
[RequireComponent(typeof(CharacterController))]
|
||||
public class PlayerController : MonoBehaviour
|
||||
{
|
||||
[Header("Input")]
|
||||
[Tooltip("Optional: the project's InputSystem_Actions asset. Actions are resolved by name from it.")]
|
||||
[SerializeField] private InputActionAsset actionsAsset;
|
||||
[Tooltip("Optional explicit references. Take priority over actionsAsset when set.")]
|
||||
[SerializeField] private InputActionReference moveAction;
|
||||
[SerializeField] private InputActionReference jumpAction;
|
||||
[SerializeField] private InputActionReference sprintAction;
|
||||
|
||||
private InputAction _move;
|
||||
private InputAction _jump;
|
||||
private InputAction _sprint;
|
||||
|
||||
[Header("Movement")]
|
||||
[SerializeField] private float walkSpeed = 5f;
|
||||
[SerializeField] private float sprintMultiplier = 1.8f;
|
||||
[SerializeField] private float acceleration = 14f;
|
||||
[SerializeField] private float rotationSpeed = 14f;
|
||||
[SerializeField] private float jumpHeight = 1.4f;
|
||||
|
||||
[Header("Gravity")]
|
||||
[SerializeField] private float gravity = -22f;
|
||||
[SerializeField] private float groundedForce = -2f;
|
||||
[Tooltip("Extra ground probe at the feet, in addition to CharacterController.isGrounded.")]
|
||||
[SerializeField] private float groundCheckRadius = 0.12f;
|
||||
[Tooltip("Probe height relative to the transform origin. The capsule's feet are at y = 0.")]
|
||||
[SerializeField] private float groundCheckOffset = 0.12f;
|
||||
[SerializeField] private LayerMask groundMask = ~0;
|
||||
|
||||
[Header("Camera")]
|
||||
[SerializeField] private Transform cameraPivot;
|
||||
[Tooltip("Create a third-person camera at runtime when the scene has no Main Camera.")]
|
||||
[SerializeField] private bool createCameraIfMissing = true;
|
||||
[SerializeField] private bool controlCursor = true;
|
||||
[SerializeField] private float lookSensitivity = 0.12f;
|
||||
[SerializeField] private float pitchMin = -35f;
|
||||
[SerializeField] private float pitchMax = 70f;
|
||||
[SerializeField] private float cameraDistance = 5f;
|
||||
[SerializeField] private float cameraHeight = 1.2f;
|
||||
[SerializeField] private float cameraSideOffset = 0.6f;
|
||||
|
||||
private CharacterController _controller;
|
||||
private Vector3 _planarVelocity;
|
||||
private float _verticalVelocity;
|
||||
private bool _grounded;
|
||||
private float _yaw;
|
||||
private float _pitch = 15f;
|
||||
private Camera _camera;
|
||||
|
||||
public bool IsGrounded { get { return _grounded; } }
|
||||
public float CurrentSpeed { get { return _planarVelocity.magnitude; } }
|
||||
|
||||
private void Awake()
|
||||
{
|
||||
_controller = GetComponent<CharacterController>();
|
||||
_yaw = transform.eulerAngles.y;
|
||||
ResolveActions();
|
||||
EnableActions(true);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Prefers explicit InputActionReference fields, otherwise resolves
|
||||
/// "Player/Move", "Player/Jump" and "Player/Sprint" from the actions asset.
|
||||
/// </summary>
|
||||
private void ResolveActions()
|
||||
{
|
||||
_move = moveAction != null ? moveAction.action : null;
|
||||
_jump = jumpAction != null ? jumpAction.action : null;
|
||||
_sprint = sprintAction != null ? sprintAction.action : null;
|
||||
|
||||
if (actionsAsset == null) return;
|
||||
|
||||
if (_move == null) _move = actionsAsset.FindAction("Player/Move", false);
|
||||
if (_jump == null) _jump = actionsAsset.FindAction("Player/Jump", false);
|
||||
if (_sprint == null) _sprint = actionsAsset.FindAction("Player/Sprint", false);
|
||||
}
|
||||
|
||||
private void OnEnable()
|
||||
{
|
||||
EnableActions(true);
|
||||
if (controlCursor)
|
||||
{
|
||||
Cursor.lockState = CursorLockMode.Locked;
|
||||
Cursor.visible = false;
|
||||
}
|
||||
}
|
||||
|
||||
private void OnDisable()
|
||||
{
|
||||
if (controlCursor)
|
||||
{
|
||||
Cursor.lockState = CursorLockMode.None;
|
||||
Cursor.visible = true;
|
||||
}
|
||||
}
|
||||
|
||||
private void EnableActions(bool enable)
|
||||
{
|
||||
SetEnabled(_move, enable);
|
||||
SetEnabled(_jump, enable);
|
||||
SetEnabled(_sprint, enable);
|
||||
}
|
||||
|
||||
private static void SetEnabled(InputAction action, bool enable)
|
||||
{
|
||||
if (action == null) return;
|
||||
if (enable) action.Enable();
|
||||
else action.Disable();
|
||||
}
|
||||
|
||||
private void Update()
|
||||
{
|
||||
ReadLook();
|
||||
ReadMove();
|
||||
ApplyGravityAndJump();
|
||||
Move();
|
||||
UpdateCamera();
|
||||
}
|
||||
|
||||
private void ReadLook()
|
||||
{
|
||||
if (Mouse.current == null) return;
|
||||
Vector2 delta = Mouse.current.delta.ReadValue() * lookSensitivity;
|
||||
_yaw += delta.x;
|
||||
_pitch = Mathf.Clamp(_pitch - delta.y, pitchMin, pitchMax);
|
||||
}
|
||||
|
||||
private void ReadMove()
|
||||
{
|
||||
Vector2 input = _move != null ? _move.ReadValue<Vector2>() : Vector2.zero;
|
||||
|
||||
Quaternion yawRotation = Quaternion.Euler(0f, _yaw, 0f);
|
||||
Vector3 desired = yawRotation * new Vector3(input.x, 0f, input.y);
|
||||
if (desired.sqrMagnitude > 1f) desired.Normalize();
|
||||
|
||||
float speed = walkSpeed;
|
||||
if (_sprint != null && _sprint.IsPressed())
|
||||
speed *= sprintMultiplier;
|
||||
|
||||
_planarVelocity = Vector3.MoveTowards(_planarVelocity, desired * speed, acceleration * Time.deltaTime);
|
||||
}
|
||||
|
||||
private void ApplyGravityAndJump()
|
||||
{
|
||||
// CharacterController.isGrounded is the authoritative check (its capsule
|
||||
// matches the visual): the extra sphere probe only helps on slopes/steps.
|
||||
Vector3 origin = transform.position + Vector3.up * groundCheckOffset;
|
||||
bool probeHit = Physics.CheckSphere(origin, groundCheckRadius, groundMask, QueryTriggerInteraction.Ignore);
|
||||
_grounded = _controller.isGrounded || probeHit;
|
||||
|
||||
if (_grounded && _verticalVelocity < 0f) _verticalVelocity = groundedForce;
|
||||
|
||||
bool wantsJump = _jump != null && _jump.WasPressedThisFrame();
|
||||
if (wantsJump && _grounded)
|
||||
_verticalVelocity = Mathf.Sqrt(jumpHeight * -2f * gravity);
|
||||
|
||||
_verticalVelocity += gravity * Time.deltaTime;
|
||||
}
|
||||
|
||||
private void Move()
|
||||
{
|
||||
Vector3 motion = _planarVelocity + Vector3.up * _verticalVelocity;
|
||||
_controller.Move(motion * Time.deltaTime);
|
||||
|
||||
if (_planarVelocity.sqrMagnitude > 0.05f)
|
||||
{
|
||||
Quaternion target = Quaternion.LookRotation(_planarVelocity.normalized, Vector3.up);
|
||||
transform.rotation = Quaternion.Slerp(transform.rotation, target, rotationSpeed * Time.deltaTime);
|
||||
}
|
||||
}
|
||||
|
||||
private void UpdateCamera()
|
||||
{
|
||||
if (_camera == null)
|
||||
{
|
||||
_camera = Camera.main;
|
||||
if (_camera == null && createCameraIfMissing)
|
||||
_camera = CreateFallbackCamera();
|
||||
if (_camera == null) return;
|
||||
}
|
||||
|
||||
Transform pivot = cameraPivot != null ? cameraPivot : transform;
|
||||
Vector3 pivotPoint = pivot.position + Vector3.up * cameraHeight + pivot.right * cameraSideOffset;
|
||||
Quaternion rotation = Quaternion.Euler(_pitch, _yaw, 0f);
|
||||
Vector3 position = pivotPoint + rotation * new Vector3(0f, 0f, -cameraDistance);
|
||||
_camera.transform.SetPositionAndRotation(position, rotation);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Builds a third-person camera at runtime so the prefab is playable even in
|
||||
/// a scene that has no camera. Only used when not overridden by an existing Main Camera.
|
||||
/// </summary>
|
||||
private static Camera CreateFallbackCamera()
|
||||
{
|
||||
GameObject cameraObject = new GameObject("PlayerCamera");
|
||||
cameraObject.tag = "MainCamera";
|
||||
Camera camera = cameraObject.AddComponent<Camera>();
|
||||
camera.fieldOfView = 60f;
|
||||
camera.nearClipPlane = 0.1f;
|
||||
camera.farClipPlane = 1000f;
|
||||
cameraObject.AddComponent<AudioListener>();
|
||||
return camera;
|
||||
}
|
||||
|
||||
private void OnDrawGizmosSelected()
|
||||
{
|
||||
Gizmos.color = Color.yellow;
|
||||
Gizmos.DrawWireSphere(transform.position + Vector3.up * groundCheckOffset, groundCheckRadius);
|
||||
}}
|
||||
@@ -1,2 +0,0 @@
|
||||
fileFormatVersion: 2
|
||||
guid: b6780c1c0b9d27c46a0bd43f0d2291f6
|
||||
Reference in New Issue
Block a user