我有一个名为 Player 的游戏对象,附加有具有以下设置的 CharacterController 组件。
Player 还附有一个名为
PlayerController
的脚本。 Update()
中调用。
private void ApplyGravity()
{
if (!characterController.isGrounded)
{
moveDirection.y -= gravity * Time.deltaTime;
}
}
Player有一个名为PlayerModel的子游戏对象,它只附加了一个默认的CapsuleCollider。
PlayerController
还有一个附加功能,称为MoveAround()
,在Update()
中也有调用;如果这与问题有关。
public void MoveAround()
{
Vector2 moveInput = playerInputActions.Player.Move.ReadValue<Vector2>();
currentInput = new Vector2(moveInput.y, moveInput.x);
float moveDirectionY = moveDirection.y;
float speed = isSprinting ? sprintSpeed : walkSpeed;
moveDirection = (transform.forward * currentInput.x + transform.right * currentInput.y) + boatController.boatRigidbody.velocity;
moveDirection.y = moveDirectionY;
moveDirection.Normalize();
moveDirection *= speed;
}
我有一个名为 Boat 的游戏对象,它附加了默认的 BoxCollider、Rigidbody 和
BoatController
脚本;
Rigidbody 有以下设置。
船漂浮在水面上,因此上下移动。
玩家 位于船 的表面。
当 Boat 漂浮起来时,Player 也随之被向上推。当它向下浮动时,会调用
ApplyGravity()
函数,从而使 Player 随之返回。
问题是这个过程并不顺利。
的 玩家被推上来时和落下时会在碰撞点抖动。
我尝试尝试将 Player 位置捕捉到 Boat 的表面,但这会导致同样的问题。
在此基础上,我还尝试使用
Physics.Raycast()
和 Vector3.Lerp()
的组合来抓取表面位置,并将 Player 分别平滑地移动到该位置;这导致了一些奇怪的错误(但我可能错误地实现了它)。
非常感谢任何有关如何解决此问题的建议。
这是正常的,因为你没有考虑框架的演变。通常要根据帧进行平滑,最好的解决方案是乘以
UnityEngine.Time.deltaTime
。由于这是一个物理函数,所以最好的选择是使用 UnityEngine.Time.fixedDeltaTime
,但应该调用相对的 FixedUpdate()
而不是 Update()
事件。
尝试:
moveDirection *= speed * Time.fixedDeltaTime;
但请确保您的堆栈跟踪是从
FixedUpdate()
启动的。当涉及物理时,这是帧更新事件的首选版本。是的,你也可以使用Update()
,但精度不一样。