UPDATE: I figured out it’s because I’m clamping X and Z velocity but not Y velocity, so I’m moving slowly forward but my Y velocity is allowed to just go insane. That being said, I don’t know an elegant solution of clamping Y velocity while still allowing Gravity to act ‘naturally’ on my Player rigidbody.
ORIGINAL POST:
Desired behavior: Controller gets slower upon hitting steep slope and/or isn’t able to move up it because it’s too steep
Current behavior: Controller can just run up a ramp and go completely airborne. Feels very physically unnatural. Gif of this happening:
delightfulmediumanteater
Why might this be happening? How might this board suggest altering the code to make the slope movement more natural?
Current code below…
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class Movement : MonoBehaviour
{
Rigidbody r;
public CapsuleCollider capsule;
public Transform cameraTransform;
//Base Movement
public float horizontalInput;
public float verticalInput;
public Vector3 moveDirection;
public Vector3 moveDirectionRaw;
public int rotDegPerSecond = 720;
public float speed;
public float maxSpeed;
//GroundChecking
public LayerMask groundLayerMask;
public Transform groundCheckTransform;
public bool isGrounded;
public float groundCheckRadius = 0.25f;
public float distanceToGround;
void Awake()
{
r = GetComponent<Rigidbody>();
capsule = GetComponent<CapsuleCollider>();
}
void Update()
{
horizontalInput = Input.GetAxis("Horizontal");
verticalInput = Input.GetAxis("Vertical");
}
private void FixedUpdate()
{
moveDirection = new Vector3(horizontalInput, 0.0f, verticalInput).normalized;
moveDirection = (Quaternion.AngleAxis(cameraTransform.rotation.eulerAngles.y, Vector3.up) * moveDirection).normalized;
moveDirectionRaw = new Vector3(Input.GetAxisRaw("Horizontal"), 0.0f, Input.GetAxisRaw("Vertical")).normalized;
moveDirectionRaw = (Quaternion.AngleAxis(cameraTransform.rotation.eulerAngles.y, Vector3.up) * moveDirectionRaw).normalized;
if (moveDirectionRaw != Vector3.zero && moveDirection != Vector3.zero)
{
Quaternion targetRotation = Quaternion.LookRotation(moveDirection); //or moveDirectionRaw
targetRotation = Quaternion.RotateTowards(transform.rotation, targetRotation, rotDegPerSecond * Time.deltaTime);
r.MoveRotation(targetRotation);
}
Vector3 force = moveDirection * speed;
r.AddForce(force, ForceMode.Force);
}
Vector3 velocityH = new Vector3(r.velocity.x, 0, r.velocity.z);
Vector3 velocityV = new Vector3(0, r.velocity.y, 0);
r.velocity = Vector3.ClampMagnitude(velocityH, 5) + velocityV;
print(r.velocity.x + " " + r.velocity.y + " " + r.velocity.z);
GroundStopSlide();
GroundCheck();
}
void GroundStopSlide()
{
if (moveDirectionRaw == Vector3.zero)
{
Vector3 zeroMe = new Vector3(0, r.velocity.y, 0);
r.velocity = zeroMe;
}
}
public void GroundCheck()
{
isGrounded = Physics.CheckSphere(groundCheckTransform.position, groundCheckRadius, groundLayerMask);
}
}