protected override void OnShow(object userData)
        {
            base.OnShow(userData);



            Vector3 startPosition = entityDataProjectile.FiringPoint.position;
            Vector3 targetPoint;

            if (fireMode == BallisticFireMode.UseLaunchSpeed)
            {
                // use speed
                targetPoint = Ballistics.CalculateBallisticLeadingTargetPointWithSpeed(
                    startPosition,
                    entityDataProjectile.EntityTargetable.transform.position, entityDataProjectile.EntityTargetable.Velocity,
                    startSpeed, arcPreference, Physics.gravity.y, 4);
            }
            else
            {
                // use angle
                targetPoint = Ballistics.CalculateBallisticLeadingTargetPointWithAngle(
                    startPosition,
                    entityDataProjectile.EntityTargetable.transform.position, entityDataProjectile.EntityTargetable.Velocity, firingAngle,
                    arcPreference, Physics.gravity.y, 4);
            }

            FireAtPoint(startPosition, targetPoint);
        }
        /// <summary>
        /// Fires this projectile from a designated start point to a designated world coordinate.
        /// Automatically sets firing angle to suit launch speed unless angle is overridden, in which case launch speed is overridden to suit angle.
        /// </summary>
        /// <param name="startPoint">Start point of the flight.</param>
        /// <param name="targetPoint">Target point to fly to.</param>
        public virtual void FireAtPoint(Vector3 startPoint, Vector3 targetPoint)
        {
            transform.position = startPoint;

            Vector3 firingVector;

            switch (fireMode)
            {
            case BallisticFireMode.UseLaunchSpeed:
                firingVector =
                    Ballistics.CalculateBallisticFireVectorFromVelocity(startPoint, targetPoint, startSpeed, arcPreference);
                firingAngle = Ballistics.CalculateBallisticFireAngle(startPoint, targetPoint, startSpeed, arcPreference);
                break;

            case BallisticFireMode.UseLaunchAngle:
                firingVector = Ballistics.CalculateBallisticFireVectorFromAngle(startPoint, targetPoint, firingAngle);
                startSpeed   = firingVector.magnitude;
                break;

            default:
                throw new ArgumentOutOfRangeException();
            }

            Fire(firingVector);
        }
        protected override void OnShow(object userData)
        {
            base.OnShow(userData);

            enemy = entityDataProjectile.EntityTargetable;

            Vector3 startingPoint = entityDataProjectile.FiringPoint.position;
            Vector3 targetPoint   = Ballistics.CalculateLinearLeadingTargetPoint(
                startingPoint, enemy.transform.position,
                enemy.Velocity, startSpeed,
                acceleration);


            Vector3 direction = entityDataProjectile.FiringPoint.forward;

            Vector3    binormal = Vector3.Cross(direction, Vector3.up);
            Quaternion rotation = Quaternion.AngleAxis(fireVectorXRotationAdjustment, binormal);

            Vector3 adjustedFireVector = rotation * direction;

            FireInDirection(startingPoint, adjustedFireVector);
        }
        protected Vector3 GetHeading()
        {
            if (enemy == null)
            {
                return(Vector3.zero);
            }
            Vector3 heading;

            if (leadTarget)
            {
                heading = Ballistics.CalculateLinearLeadingTargetPoint(transform.position, enemy.transform.position,
                                                                       m_TargetVelocity, m_Rigidbody.velocity.magnitude,
                                                                       acceleration,
                                                                       leadingPrecision) - transform.position;
            }
            else
            {
                heading = enemy.transform.position - transform.position;
            }

            return(heading.normalized);
        }
        /// <summary>
        /// Fires this projectile from a designated start point to a designated world coordinate.
        /// </summary>
        /// <param name="startPoint">Start point of the flight.</param>
        /// <param name="targetPoint">Target point to fly to.</param>
        public virtual void FireAtPoint(Vector3 startPoint, Vector3 targetPoint)
        {
            transform.position = startPoint;

            Fire(Ballistics.CalculateLinearFireVector(startPoint, targetPoint, startSpeed));
        }