A* Pathfinding Project

Determine if agent will arrive to destination on next frame


#1

Hello, I have some questions:

QUESTION 1:
I would like to know how to determine if an agent will arrive to the destination on the next frame.

I need this because I am making a unit follow a circular path around a target.
… but if the unit is moving too fast it gets significantly slowed down every time it reaches the destination.
So I would like to give it the next point in the path if it’s too close to it.

However this could allow the unit to follow any path correctly. Thus the answer would be very useful.

Normally the unit should move in circles much faster than that because it has a huge acceleration (150 units)

I am interested in reproducing this behaviour: https://youtu.be/JQidNsfV2YA?t=23 where the unit circles around the player. (I don’t want the unit to travel on the walls like in that game however)

Here is what I’m using in code (this will only check for to the next point, it would be nice if I could skip more than one point depending on my unit’s movement speed):

    public Vector3 AiGetMove(float _speed, out Quaternion _rotation, bool _slowWhenNotFacingTarget, float _slowDownFactor = .5f)
    {
        ai.maxSpeed = _speed;

        ai.MovementUpdate(Time.deltaTime, out var dest, out var rot);
        _rotation = rot;
        var deltaMove = (dest - this.transform.position);

        if (deltaMove.sqrMagnitude < .00001f)
        {
            return Vector3.zero;
        }

        var velocity = deltaMove / Time.deltaTime;

        if (_slowWhenNotFacingTarget)
        {
            // Slowdown...
            Debug.Log("prevel: " + velocity);
            var forward = this.transform.forward;
            forward = new Vector2(forward.x, forward.z).normalized;
            var velXY = MovementUtilities.ClampVelocity(new Vector2(velocity.x, velocity.z), ai.maxSpeed, 1f, _slowWhenNotFacingTarget,
                forward);
            Debug.Log("velXY: " + velXY);

            velocity = new Vector3(velXY.x, 0f, velXY.y);
        }

        return velocity;
    }

    public Vector3 AiDoMove(float _maxSpeed, Movement _move = Movement.AllowRotation, bool _slowWhenNotFacingTarget = false, float _slowDownFactor = .5f)
    {
        var vel = AiGetMove(_maxSpeed, out var rot, _slowWhenNotFacingTarget);

        //        ai.FinalizeMovement(dest, rot);
        Control.Move(vel, _move);

        return vel;
    }

    /// <summary>
    /// Set and search path to destination. Sets the pathPending to true.
    /// </summary>
    public void SetDestination(Vector3 _destination, bool _directSearch = true)
    {
        ai.destination = _destination;
        if (_directSearch)
            ai.SearchPath();
    }

    public Vector3 AiDoPath(List<Vector3> _points, ref int _currentIndex, float _maxSpeed, out bool onPathFinished)
    {
        bool forceRecalculation = false;
        onPathFinished = false;

//        var expectedMovement = ai.desiredVelocity.magnitude * Time.deltaTime;
//        var mag = ai.desiredVelocity.magnitude;
//        Debug.Log($"ai.desiredVelocity.magnitude: {mag}");
//        Debug.Log($"ai.desiredVelocity.deltaTimed: {mag * Time.deltaTime}");
//        Debug.Log($"_maxSpeed: {_maxSpeed}");
//        Debug.Log($"ai.remainingDistance: {ai.remainingDistance}");
//        var expectedMovement =_maxSpeed * Time.deltaTime;
        if (AiIsPathDone() /*|| ai.remainingDistance < expectedMovement*/)
        {
            // Set next destination...
            _currentIndex = (_currentIndex + 1);

            if (_currentIndex > _points.Count)
            {
                onPathFinished = true;
                return Vector3.zero;
            }

            forceRecalculation = true;
        }

        SetDestination(_points[_currentIndex], forceRecalculation);

        return AiDoMove(_maxSpeed);
    }

QUESTION 2:
Is it a good idea to even make custom paths for AI [with pathfinding] or is it really complicated because the unit won’t even follow the path as soon as there are obstacles?
Are ONLY linear paths recommended with pathfinding?


#2

Hi

You can use ai.remainingDistance to get the approximate distance to the current end of the path. That should help.
You should be able to get a reasonable behaviour if you make sure that the target point is ahead of the unit by at least maybe 1ai.maxSpeed or 2ai.maxSpeed.

Also. You might want to set ai.slowdownDistance or ai.slowdownTime (depending on which movement script you are using) to zero. This will make it not slow down at all when approaching the destination.