Unity – 计算相对于瞄准的移动向量以制作侧移动画 [已解决]

huangapple go评论82阅读模式
英文:

Unity - Calculate movement vector relative to aim in order to make strafe animations [SOLVED]

问题

我正在Unity中制作一个3D顶视射击游戏,我遇到了一个问题。相机是固定的,不会旋转,所以当你按下左键时,它会旋转玩家并向左移动。这部分运作良好,但问题是玩家瞄准时。在我的游戏中,玩家可以在按住鼠标右键时瞄准。我想在瞄准时制作侧移动画。我在动画器中创建了这个混合树:

[![混合树][1]][1]

我在那里有两个参数:AimingWalkHorizontal和AimingWalkVertical。当值为[1,0]时,它会播放向右侧移动动画。

我有两个向量。一个用于移动,一个用于瞄准:

```csharp
Vector3 movementVector = new Vector3(_movementVector.x, 0, _movementVector.y);
Vector3 aimingDirection = new Vector3((MouseWorldPosition - PlayerController.PlayerObj.transform.position).x, 0, (MouseWorldPosition - PlayerController.PlayerObj.transform.position).z);

我想实现这个效果:

[![在这里输入图像描述][2]][2]

我如何获得这个相对移动向量以传递给动画器?

PlayerController.Animator.SetFloat("AimingWalkHorizontal", /* ??? */);
PlayerController.Animator.SetFloat("AimingWalkVertical", /* ??? */);

谢谢


<details>
<summary>英文:</summary>

I am making 3D top down shooter in Unity and I am facing a problem. Camera is fixed and is not rotating, so when you press left button it will rotate the player and move forwards to left. It is working well, but problem is when player is aiming. In my game player has ability to aim while holding right mouse button. I want to make strafe animations while aiming. I have created this blend tree in animator:

[![Blend tree][1]][1]

I have two parameters there: AimingWalkHorizontal and AimingWalkVertical. When the values are [1,0] it will play strafe right animation.

I have two Vectors. One for movement and one for aiming:

    Vector3 movementVector = new Vector3(_movementVector.x, 0, _movementVector.y);
    Vector3 aimingDirection = new Vector3((MouseWorldPosition - PlayerController.PlayerObj.transform.position).x, 0, (MouseWorldPosition - PlayerController.PlayerObj.transform.position).z);

And I want to achieve this:

[![enter image description here][2]][2]

How can I get this relative movement Vector in order to feed it to animator?

    PlayerController.Animator.SetFloat(&quot;AimingWalkHorizontal&quot;, /* ??? */);
    PlayerController.Animator.SetFloat(&quot;AimingWalkVertical&quot;, /* ??? */);

Thank you




  [1]: https://i.stack.imgur.com/vQ0YF.png
  [2]: https://i.stack.imgur.com/wDnKs.png

</details>


# 答案1
**得分**: 0

我已经通过计算移动和瞄准向量之间的顺时针角度来解决了这个问题。然后我将角度转换为规范化向量,然后将其推送到动画师。

```csharp
Vector3 movementVector = new Vector3(_movementVector.x, 0, _movementVector.y).normalized;
Vector3 aimingDirection = new Vector3((MouseWorldPosition - PlayerController.PlayerObj.transform.position).x, 0, (MouseWorldPosition - PlayerController.PlayerObj.transform.position).z).normalized;

// 计算移动和瞄准方向之间的顺时针角度
float dotProduct = Vector3.Dot(movementVector, aimingDirection);
float crossProductMagnitude = Vector3.Cross(movementVector, aimingDirection).y;
float clockwiseAngle = Mathf.Atan2(crossProductMagnitude, dotProduct) * Mathf.Rad2Deg;

// 在我的游戏中,我可以用中键旋转相机,所以我必须减小角度以考虑相机旋转
// 如果你的相机旋转是固定的,请不要使用这行
clockwiseAngle -= CameraController.Instance.CameraObj.transform.eulerAngles.y;

// 调整角度为正值(0到360度)
clockwiseAngle = (clockwiseAngle + 360) % 360;

// 将角度转换为规范化向量

// 转换为弧度
float radians = clockwiseAngle * Mathf.Deg2Rad;

// 计算向量轴
float x = Mathf.Cos(radians);
float z = Mathf.Sin(radians);

// 创建规范化向量
Vector3 relativeMovement = new Vector3(x, 0f, z).normalized;

// 设置动画师的值
PlayerController.Animator.SetFloat("AimingWalkHorizontal", relativeMovement.z * -1f);
PlayerController.Animator.SetFloat("AimingWalkVertical", relativeMovement.x);
英文:

I have finally solved it by calculating clockwise angle between movement and aim vector. Than I am converting angle to normalized vector that is pushed to animator.

Vector3 movementVector = new Vector3(_movementVector.x, 0, _movementVector.y).normalized;
Vector3 aimingDirection = new Vector3((MouseWorldPosition - PlayerController.PlayerObj.transform.position).x, 0, (MouseWorldPosition - PlayerController.PlayerObj.transform.position).z).normalized;

// Calculate clockwise angle between movement and aiming direction
float dotProduct = Vector3.Dot(movementVector, aimingDirection);
float crossProductMagnitude = Vector3.Cross(movementVector, aimingDirection).y;
float clockwiseAngle = Mathf.Atan2(crossProductMagnitude, dotProduct) * Mathf.Rad2Deg;

// In my game I have ability to rotate camera with middle mouse button, so I have to decrease angle by camera rotation
// If you have fixed camera rotation do not use this line
clockwiseAngle -= CameraController.Instance.CameraObj.transform.eulerAngles.y;

// Adjust the angle to be positive (0 to 360 degrees)
clockwiseAngle = (clockwiseAngle + 360) % 360;

// Convert angle to normalized vector

// Convert to radians
float radians = clockwiseAngle * Mathf.Deg2Rad;

// Calculate vector axis
float x = Mathf.Cos(radians);
float z = Mathf.Sin(radians);

// Create normalized vector
Vector3 relativeMovement = new Vector3(x, 0f, z).normalized;

// Set values to animator
PlayerController.Animator.SetFloat(&quot;AimingWalkHorizontal&quot;, relativeMovement.z * -1f);
PlayerController.Animator.SetFloat(&quot;AimingWalkVertical&quot;, relativeMovement.x);

huangapple
  • 本文由 发表于 2023年7月13日 14:44:39
  • 转载请务必保留本文链接:https://go.coder-hub.com/76676588.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定