public CalculationResult Calculate(AccelerationPolarity accelerationPolarity, double timeToNode, double distanceToNode, double currentSpeed)
        {
            var result = new CalculationResult();

            CorrectAccelerationToPolarity(accelerationPolarity, AccelerationMagnitude);

            var argsCheckResult = ValidateArguments(distanceToNode, timeToNode, currentSpeed, ReactionTime, AccelerationMagnitude);

            if (argsCheckResult != CalculationErrors.NoErrors)
            {
                // Error detected.
                result.AdvisorySpeed = null;
            }
            else
            {
                var advisorySpeed = currentSpeed + AccelerationMagnitude * (timeToNode - ReactionTime -
                                                                            Math.Sqrt(Math.Pow(timeToNode - ReactionTime, 2) - (2 * (distanceToNode - timeToNode * currentSpeed)) / AccelerationMagnitude)
                                                                            );

                result.AdvisorySpeed = advisorySpeed;
            }

            result.Errors = argsCheckResult;
            return(result);
        }
        public static CalculationResult CalculateAdvisorySpeed(int distance, double timeToIntersection, double currentSpeed, AdvisoryCalculatorMode advisoryCalculatorMode)
        {
            CalculationResult calculationResult = new CalculationResult();

            calculationResult.AdvisorySpeed = -1;
            calculationResult.Errors        = CalculationErrors.NoErrors;

            if (advisoryCalculatorMode == AdvisoryCalculatorMode.Advanced)
            {
                AdvancedAdvisorySpeedCalculator advancedAdvisorySpeedCalculator = new AdvancedAdvisorySpeedCalculator();
                calculationResult = advancedAdvisorySpeedCalculator.Calculate(AccelerationPolarity.Decelerate, timeToIntersection, distance, currentSpeed);
            }
            else
            {
                BasicSpeedAdvisoryCalculator calculator = new BasicSpeedAdvisoryCalculator();
                calculationResult = calculator.Calculate(distance, timeToIntersection);
            }

            var speedMPH = Convert.ToInt32(calculationResult.AdvisorySpeed) < 0 ? 0 : Convert.ToInt32(calculationResult.AdvisorySpeed);

            speedMPH = Convert.ToInt32(SpeedConverter.ConvertFromMetersPerSecondToMilePerHour(speedMPH));
            if (speedMPH > Settings.SpeedLimit)
            {
                calculationResult.Errors = CalculationErrors.AdvisorySpeedAboveSpeedLimit;
            }
            else if (speedMPH < (Settings.SpeedLimit / 2))
            {
                calculationResult.Errors = CalculationErrors.AdvisorySpeedBelowHalfSpeedLimit;
            }

            return(calculationResult);
        }
        /// <summary>
        ///
        /// </summary>
        /// <param name="distance"></param>
        /// <param name="timespanToCurrentMovementStateEnd"></param>
        /// <returns></returns>
        public CalculationResult Calculate(double distance, double timespanToCurrentMovementStateEnd)
        {
            CalculationResult result = new CalculationResult();

            result.AdvisorySpeed = GetAdvisorySpeed(distance, timespanToCurrentMovementStateEnd);

            return(result);
        }