简体   繁体   English

Unity3D:改善播放器的动画

[英]Unity3D: Improving player's animation

I have a 2d RPG click to move game. 我有2D RPG点击移动游戏。 I want to improve my code so that my players animation doesn't look bad, for example this is a video of what my player's animation looks like. 我想改进代码,以使播放器的动画看起来不错,例如,这是播放器动画的视频 As you can see my player's idle state animation isn't the best. 如您所见,播放器的空闲状态动画不是最好的。 The video also allows you to see my animator, just in case if I have made a mistake within my blend tree or transitions. 该视频还允许您查看我的动画师,以防万一我在混合树或过渡中犯了一个错误。 How can I improve my code so that my player's animation isn't bad and my player's idle state animation face the correct direction it is suppose to be facing. 我该如何改善代码,以使播放器的动画效果不错并且播放器的空闲状态动画面对应该面对的正确方向。 Thank you! 谢谢!

private Animator anim;
public float speed = 15f;
private Vector3 target;
private bool touched;
private bool playerMovementRef;


void Start()
{
    target = transform.position;
    anim = GetComponent<Animator>();
}
void Update()
{
    if (Input.GetMouseButtonDown(0))
    {
        Vector3 mousePosition = Input.mousePosition;
        mousePosition.z = 10; // distance from the camera
        target = Camera.main.ScreenToWorldPoint(mousePosition);
        target.z = transform.position.z;

        var movementDirection = (target - transform.position).normalized;

        if (movementDirection.x != 0 || movementDirection.y != 0)
        {
            anim.SetBool("walking", true);
            anim.SetFloat("SpeedX", movementDirection.x);
            anim.SetFloat("SpeedY", movementDirection.y);

            if (movementDirection.x < 0)
            {
                anim.SetFloat("LastMoveX", -1f);
            }
            else if (movementDirection.x > 0)
            {
                anim.SetFloat("LastMoveX", 1f);
            }
            else
            {
                anim.SetFloat("LastMoveX", 0f);
            }
            if (movementDirection.y > 0)
            {
                anim.SetFloat("LastMoveY", 1f);
            }
            else if (movementDirection.y < 0)
            {
                anim.SetFloat("LastMoveY", -1f);
            }
            else
            {
                anim.SetFloat("LastMoveY", 0f);
            }
        }
    }
    else
    {
        if (Mathf.Approximately(transform.position.x, target.x) && Mathf.Approximately(transform.position.y, target.y))
        {
            touched = false;
            anim.SetBool("walking", false);
        }
        else
        {
            transform.position = Vector3.MoveTowards(transform.position, target, speed * Time.deltaTime);
        }
    }
}
  }

To be more clear, I want to do something like this: http://imgur.com/j7gBeDA But I'm having problems with my code, I'm close it's just isn't facing correctly when it goes to it's idle state. 更清楚地说,我想做这样的事情: http : //imgur.com/j7gBeDA但是我的代码有问题,我很接近,它进入空闲状态时并没有正确面对。 I've check if "has exit time" was on, which it was not, so I'm not sure what I am doing wrong. 我已经检查了“是否有退出时间”,是否没有,所以我不确定自己做错了什么。 I also made sure that I debug.log it and it didn't exactly give me an answer to what I was looking for. 我还确保我将debug.log记录下来,但它并没有完全为我寻找的答案。

At present you are using a crude bunch of if-then blocks to set various floats in the mechanim controller, which in the end controls the direction the character is facing. 目前,您正在使用粗略的if-then块在mechanim控制器中设置各种浮点数,该浮点数最终控制角色面对的方向。 It is possible (in fact extremely likely) for both movementDirection.x and movementDirection.y to be non-negative. 这是可能的(事实上极有可能) 两个 movementDirection.xmovementDirection.y为非负。 However, your animation panels are only four-directional, so you need to convert the 2D vector to one which has only one non-zero value between its x and y . 但是,动画面板只有四个方向,因此您需要将2D向量转换为一个在xy之间只有一个非零值的向量。

Vector3 animDirection = Vector3.zero;

if (movementDirection.sqrMagnitude > 0)
{
    // Use >= to default to horizontal on both being equal
    if (movementDirection.x > movementDirection.y) 
        animDirection.x = 1;
    else
        animDirection.y = 1;
}

In your idle animation you have a blend tree with four different states in Freeform Cartesian. 在您的空闲动画中,您有一个混合树,在自由格式笛卡尔中具有四个不同的状态。 The problem is you only have four discrete animations to choose from, not an infinite range of motion as would be the case in 3d. 问题是您只有四个离散的动画可供选择,而不是像3d那样无限的运动范围。 It looks like what's happening is that you're getting non-zero values for each of LastMoveX and LastMoveY. 看来正在发生的事情是您为LastMoveX和LastMoveY的每个获取非零值。 Because of that the result puts your animation in one corner of the blend tree - right between two states. 因此,结果会将您的动画放在混合树的一个角上-介于两个状态之间。 I think the only thing determining which way the end result faces is floating point imprecision. 我认为确定最终结果面对的唯一方法是浮点不精确度。 To solve the issue you can boil down the logic of the idle state to it's four components, a single variable would probably work, and just have each animation assigned to a value. 要解决此问题,您可以将空闲状态的逻辑归结为四个部分,一个变量可能会起作用,并且只需将每个动画分配一个值即可。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM