将对象平滑旋转到一个值[重复]

Posted

技术标签:

【中文标题】将对象平滑旋转到一个值[重复]【英文标题】:Rotate an object smoothly to a value [duplicate] 【发布时间】:2022-01-14 12:15:18 【问题描述】:

我有一个可以在 z 轴和 y 轴上旋转的飞机控制器。当上/下或左/右输入 == 0 时,我希望平面旋转重置(再次变为水平)。

经过一些试验和错误,这可行:

if (Input.GetAxis("Horizontal") == 0.0f && transform.rotation.z != 0f) 
  Vector3 tempRotation = new Vector3();
  tempRotation.z = 0.0f;
  transform.rotation = Quaternion.Euler(tempRotation);

但是,它会立即卡入到位。我希望它是一个渐进的轮换。这也会对相机产生负面影响(也包括快照)。

我为每个更新周期等尝试了tempRotation.z -= 0.1f; 之类的东西,但是当它变为 0 时这并没有停止(我不知道为什么):

if (Input.GetAxis("Horizontal") == 0.0f && transform.rotation.z != 0.0f) 
  Vector3 tempRotation = transform.rotation.eulerAngles;
  tempRotation.z = (float) Math.Round(tempRot.z, 1);
  tempRotation.z += 0.1f;
  transform.rotation = Quaternion.Euler(tempRotation);

有人知道吗?谢谢。

【问题讨论】:

【参考方案1】:

首先,不要使用transform.rotation.z,除非你对四元数了如指掌。您可能打算使用transform.eulerAngles.z

可以查看local right的y分量判断是否倾斜,使用Quaternion.LookRotation查找“重置”旋转,这比使用eulerAngles安全一点。

然后,您必须进行旋转。对于一个非常简单的恒定速度,您可以使用Quaternion.RotateTowards 向它旋转:

[SerializeField] float resetSpeed;

// ...

if (Input.GetAxis("Horizontal") == 0.0f && !Mathf.Approximately(transform.right.y, 0f))

    Quaternion startRot = transform.rotation;
    Quaternion goalRot = Quaternion.LookRotation(transform.forward);
    transform.rotation = Quaternion.RotateTowards(startRot, goalRot, 
            resetSpeed * Time.deltaTime);


if (Input.GetAxis("Vertical") == 0.0f && !Mathf.Approximately(transform.forward.y, 0f))

    Quaternion startRot = transform.rotation;
    Quaternion goalRot = Quaternion.LookRotation(Vector3.Scale(transform.forward,
            Vector3(1f,0f,1f)), transform.up);
    transform.rotation = Quaternion.RotateTowards(startRot, goalRot, 
            resetSpeed * Time.deltaTime);

【讨论】:

这是完美的@Ruzihm,非常感谢! 我现在正试图让它也适用于上/下旋转,知道为什么这不起作用吗?结合起来,我可以在LookRotation 中添加transform.uptransform.forward 吗? cs if (Input.GetAxis("Vertical") == 0.0f && !Mathf.Approximately(transform.up.z, 0f)) Quaternion startRot = transform.rotation; Quaternion goalRot = Quaternion.LookRotation(transform.up); transform.rotation = Quaternion.RotateTowards(startRot, goalRot, resetSpeed * Time.deltaTime); 我会在单独的if 中为"Vertical" 做同样的事情。只有goalRot = Quaternion.LookRotation(Vector3.Scale(new Vector3(1f,0f,1f), transform.forward), transform.up);,你可以检查!Mathf.Approximately(transform.forward.y, 0f) 太棒了,非常感谢。看 Unity 文档时我有点困惑——它指的是颜色,它们根据是指场景还是对象而有所不同。非常感谢您的帮助!

以上是关于将对象平滑旋转到一个值[重复]的主要内容,如果未能解决你的问题,请参考以下文章

AVCaptureVideoPreviewLayer 平滑方向旋转

将溢出的 divv 平滑滚动到其中的特定位置[重复]

旋转父游戏对象

使用触摸平滑旋转 UIView

uinty实现玩家尾随鼠标位置平滑旋转角度

javascript将数组作为值添加到对象[重复]