News Forums RAIN General Discussion and Troubleshooting Anyone who can help me with Fixing my RAIN Motor for A* Pathfinding

Tagged: ,

This topic contains 0 replies, has 1 voice, and was last updated by  pedroJDM 3 weeks, 6 days ago.

Viewing 1 post (of 1 total)
  • Author
    Posts
  • #40499

    pedroJDM
    Participant

    Hello i was writing my own custom motor to get rain Ai working with the arongranberg A* Pathfinding Project ( Free version ), i getting it working but when it callculates a new path i get “lag” on the movement ..

    if anyone can help me with this i will be very Grateful with that

    so here is the code:

    using UnityEngine;
    using System.Collections;
    using RAIN.Serialization;
    using RAIN.Motion;
    using Pathfinding;
    [RAINSerializableClass]
    public class AstarMotor : RAINMotor
    {
        [RAINSerializableField]
        private float _rotationSpeed = 15f;
        [RAINSerializableField]
        private float _closeEnoughDistance = 3.5f;
        [RAINSerializableField]
        private float _waitpointDistcance = 3.0f;
        [RAINSerializableField]
        private float _breakSpeed = 8f;
        [RAINSerializableField]
        private float _repathTime = 0.5f;
        [RAINSerializableField]
        private bool _debug;
        private Rigidbody _Body;
        private Seeker _Seeker;
        private Path _Path;
        private int _CurrentwaypointIndex = 0;
        private Vector3 _LastPosition = Vector3.zero;
        private float timer;
        private float rtimer;
        private bool Canrepath;
        private Vector3 _destvalue;
        private Vector3 DestinationPath
        {
            get
            {
                if (_Path != null)
                {
                    if (_CurrentwaypointIndex < _Path.vectorPath.Count)
                    {
                        return _Path.vectorPath[_CurrentwaypointIndex];
                    }
                    else
                    {
                        return Destination;
                    }
                }
                else
                {
                    return AI.Kinematic.Position;
                }
            }
        }
        private Vector3 Destination
        {
            get
            {
                Path curr = _Path;
                if (curr != null && curr.vectorPath.Count > 0 )
                {
                    int lastindex = curr.vectorPath.Count - 1;
                    return curr.vectorPath[lastindex];
                }
                else
                {
                    return AI.Kinematic.Position;
                }
            }
            set
            {
                if (_Seeker != null )
                {
                    _destvalue = value;
                    Canrepath = true;
                }
            }
        }
        void OnPathComplete( Path p )
        {
            if(_debug)
                Debug.Log( AI.Body.GetInstanceID() + ": Yep ! We got a Path, has an Error?: " + p.error);
            _Path = p;
            _CurrentwaypointIndex = 0;
        }
        private float RemainingDistance
        {
            get
            {
                return Vector3.Distance(AI.Kinematic.Position, MoveTarget.Position);
            }
        }
        private float _Speed = 0;
        public override float DefaultSpeed
        {
            get
            {
                return AI.WorkingMemory.GetItem<float>("Speed");
            }
            set
            {
                AI.WorkingMemory.SetItem("Speed", value);
            }
        }
        public override float DefaultCloseEnoughDistance
        {
            get
            {
                if (MoveTarget.IsValid)
                {
                    return Mathf.Max(_closeEnoughDistance, MoveTarget.CloseEnoughDistance);
                }
                else
                {
                    return _closeEnoughDistance;
                }
            }
            set
            {
                _closeEnoughDistance = value;
            }
        }
        public override float DefaultRotationSpeed
        {
            get
            {
               return _rotationSpeed;
            }
            set
            {
                _rotationSpeed = value;
            }
        }
        void MoveCharacter()
        {
            // if we are not at our target
            if (!IsAt(MoveTarget.Position) && _Speed > 0f)
            {
                // Movement
                Vector3 MoveDir = DestinationPath - AI.Kinematic.Position;
                Vector3 Motion = MoveDir.normalized * _Speed;
                _Body.velocity = Motion;
                // Distance Check
                float wDistance = Vector3.Distance(AI.Kinematic.Position, DestinationPath);
                if (wDistance <= _waitpointDistcance)
                {
                    _CurrentwaypointIndex++;
                }
                else
                {
                    // Rotation
                    Vector3 rotateMotion = Motion.normalized;
                    rotateMotion.y = 0;
                    if (rotateMotion != Vector3.zero)
                    {
                        Quaternion tr = Quaternion.LookRotation(rotateMotion);
                        Quaternion lerprotation = Quaternion.Slerp(_Body.transform.rotation,
                         tr, _rotationSpeed * Time.deltaTime);
                        if(_debug)
                            Debug.DrawRay(AI.Kinematic.Position, rotateMotion * 10f, Color.blue);
                        AI.Body.transform.rotation = lerprotation;
                    }
                }
            }
            else
            {
                _Body.velocity = Vector3.Lerp(_Body.velocity, Vector3.zero, _breakSpeed * Time.deltaTime);
            }
        }
        public override void BodyInit()
        {
            base.BodyInit();
            _Body = AI.Body.GetComponent<Rigidbody>();
            _Seeker = AI.Body.GetComponent<Seeker>();
            if (_Body == null)
                _Body = AI.Body.AddComponent<Rigidbody>();
            if (_Seeker == null)
                _Seeker = AI.Body.AddComponent<Seeker>();
        }
        // Update 
        public override void UpdateMotionTransforms()
        {
            AI.Kinematic.ParentTransform = Matrix4x4.identity;
            AI.Kinematic.Position = AI.Body.transform.position;
            AI.Kinematic.ResetVelocities();
            if (Canrepath == true)
            {
                timer += Time.deltaTime;
                if (timer >= _repathTime)
                {
                    float distance = Vector3.Distance(Destination, _destvalue);
                    if (_Seeker != null && _Seeker.IsDone() && distance > _waitpointDistcance )
                    {
                        // _Path = null;
                        _Seeker.StartPath(AI.Kinematic.Position, _destvalue, OnPathComplete);
                        timer = 0;
                        Canrepath = false;
                    }
                }
            }
            if (MoveTarget.IsValid  )
            {
                MoveCharacter();
            }
            rtimer += Time.deltaTime;
            if (rtimer >= _repathTime)
                _Speed = 0f;
            AI.Kinematic.Orientation = AI.Body.transform.rotation.eulerAngles;
        }
        public override bool IsAt(Vector3 aPosition)
        {
            Vector3 dir = aPosition - AI.Kinematic.Position;
            dir.y = 0;
            float d = dir.magnitude;
            return d <= DefaultCloseEnoughDistance;
        }
        public override bool Move()
        {
            if (!MoveTarget.IsValid)
                return false;
            Vector3 tEndMoved = (_LastPosition - MoveTarget.Position);
            tEndMoved.y = 0;
            _Speed = DefaultSpeed;
            if (  _Path == null || !Mathf.Approximately(tEndMoved.sqrMagnitude, 0) )
            {
                Destination = MoveTarget.Position;
                _LastPosition = MoveTarget.Position;
                return IsAt(Destination);
            }
            if (_Path.CompleteState != PathCompleteState.Complete
                || _Path.CompleteState != PathCompleteState.Partial)
                return false;
            return RemainingDistance <= DefaultCloseEnoughDistance;
        }
        public override void ApplyMotionTransforms()
        {
        }
        public override bool Face()
        {
            return true;
        }
        public override bool IsAt(MoveLookTarget aTarget)
        {
            return IsAt(aTarget.Position);
        }
        public override bool IsFacing(Vector3 aPosition)
        {
            return true;
        }
        public override bool IsFacing(MoveLookTarget aTarget)
        {
            return true; 
        }
        public override void Stop()
        {
        }
        public override bool Allow3DMovement
        {
            get { return false; }
            set { }
        }
        public override bool AllowOffGraphMovement
        {
            get { return false; }
            set { }
        }
        public override bool Allow3DRotation
        {
            get { return false; }
            set { }
        }
    }
Viewing 1 post (of 1 total)

You must be logged in to reply to this topic.