Skip to content

Instantly share code, notes, and snippets.

@JackKell
Created December 16, 2019 02:42
Show Gist options
  • Select an option

  • Save JackKell/e11610d89c78b5b2d4046612d3f59af4 to your computer and use it in GitHub Desktop.

Select an option

Save JackKell/e11610d89c78b5b2d4046612d3f59af4 to your computer and use it in GitHub Desktop.
using UnityEngine;
public class JumpingCharacterControllerExample : MonoBehaviour
{
[SerializeField] private float jumpHeight;
[SerializeField] private float timeToReachJumpApex;
private Vector3 _velocity;
private Vector3 _oldVelocity;
private float _maxHeightReached = Mathf.NegativeInfinity;
private float _startHeight = Mathf.NegativeInfinity;
private bool _reachedApex = true;
private float Gravity => -2 * jumpHeight / (timeToReachJumpApex * timeToReachJumpApex);
private float JumpForce => 2 * jumpHeight / timeToReachJumpApex;
private CharacterController _characterController;
private bool _isGrounded = false;
private float _jumpTimer = 0;
private void Start()
{
_characterController = GetComponent<CharacterController>();
}
private void Jump()
{
_jumpTimer = 0;
_maxHeightReached = Mathf.NegativeInfinity;
_velocity.y = JumpForce;
_startHeight = transform.position.y;
_reachedApex = false;
}
private void Update()
{
if (_isGrounded && Input.GetButtonDown("Jump"))
{
Jump();
}
if (!_isGrounded && !_reachedApex)
{
_jumpTimer += Time.fixedDeltaTime;
}
if (!_reachedApex && _maxHeightReached > transform.position.y)
{
float delta = _maxHeightReached - _startHeight;
float error = jumpHeight - delta;
Debug.Log($"jump result: start:{_startHeight:F4}, end:{_maxHeightReached:F4}, delta:{delta:F4}, error:{error:F4}, time:{_jumpTimer:F4}, gravity:{Gravity:F4}, jumpForce:{JumpForce:F4}");
_reachedApex = true;
}
_maxHeightReached = Mathf.Max(transform.position.y, _maxHeightReached);
_oldVelocity = _velocity;
_velocity.y += Gravity * Time.fixedDeltaTime;
Vector3 deltaPosition = (_oldVelocity + _velocity) * 0.5f * Time.fixedDeltaTime;
CollisionFlags collisionFlags = _characterController.Move(deltaPosition);
_isGrounded = collisionFlags == CollisionFlags.Below;
if (_isGrounded)
{
_velocity.y = 0;
}
}
}
@moniewski
Copy link

Thanks for the comment on SebastianLague video!
I think using fixedDeltaTime in Update makes thing framerate dependent. Probably all this logic should be in FixedUpdate?
Fun fact: Time.deltaTime used in FixedUpdate automatically return Time.fixedDeltaTime. Probably they did that because people were typing things out of habit and introducing hard to debug physics bugs.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment