Example #1
0
void
OrderedTask::GlideSolutionPlanned(const AircraftState &aircraft,
                                  const GlidePolar &glide_polar,
                                    GlideResult &total,
                                    GlideResult &leg,
                                    DistanceStat &total_remaining_effective,
                                    DistanceStat &leg_remaining_effective,
                                    const GlideResult &solution_remaining_total,
                                    const GlideResult &solution_remaining_leg)
{
  TaskMacCreadyTotal tm(task_points, active_task_point,
                        task_behaviour.glide, glide_polar);
  total = tm.glide_solution(aircraft);
  leg = tm.get_active_solution();

  if (solution_remaining_total.IsOk())
    total_remaining_effective.SetDistance(tm.effective_distance(solution_remaining_total.time_elapsed));
  else
    total_remaining_effective.Reset();

  if (solution_remaining_leg.IsOk())
    leg_remaining_effective.SetDistance(tm.effective_leg_distance(solution_remaining_leg.time_elapsed));
  else
    leg_remaining_effective.Reset();
}
Example #2
0
static void
CheckLegEqualsTotal(const GlideResult &leg, const GlideResult &total)
{
  ok1(total.IsOk());
  ok1(equals(total.height_climb, leg.height_climb));
  ok1(equals(total.height_glide, leg.height_glide));
  ok1(equals(total.altitude_difference, leg.altitude_difference));
  ok1(equals(total.GetRequiredAltitudeWithDrift(), leg.GetRequiredAltitudeWithDrift()));
}
Example #3
0
  /**
   * Function to optimise in search
   *
   * \note the f(x) is magnified because with fixed, find_min can
   *   fail with too small df/dx
   *
   * @param V cruise true air speed (m/s)
   * @return Inverse LD
   */
  double f(const double v) {
    res = mac.SolveGlide(task, v, allow_partial);
    if (!res.IsOk() || res.vector.distance <= 0)
      /* the solver failed: return a large value that will be
         discarded by ZeroFinder */
      return 1000000;

    return res.height_glide * 1024 / res.vector.distance;
  }
Example #4
0
void 
UnorderedTask::GlideSolutionPlanned(const AircraftState &state, 
                                      GlideResult &total,
                                      GlideResult &leg,
                                      DistanceStat &total_remaining_effective,
                                      DistanceStat &leg_remaining_effective,
                                      const GlideResult &solution_remaining_total,
                                      const GlideResult &solution_remaining_leg)
{
  total = solution_remaining_total;
  leg = solution_remaining_leg;

  if (total.IsOk())
    total_remaining_effective.set_distance(total.vector.distance);
  else
    total_remaining_effective.Reset();

  if (leg.IsOk())
    leg_remaining_effective.set_distance(leg.vector.distance);
  else
    leg_remaining_effective.Reset();
}
Example #5
0
void
RoutePolar::Initialise(const GlidePolar& polar, const SpeedVector& wind,
                       const bool is_glide)
{
  for (unsigned i = 0; i < ROUTEPOLAR_POINTS; ++i) {
    const Angle ang = IndexToAngle(i);
    GlideResult res = SolveTask(polar, wind, ang, is_glide);
    if (res.IsOk()) {
      RoutePolarPoint point(res.time_elapsed, res.height_glide);
      points[i] = point;
    } else
      points[i].valid = false;
  }
}
Example #6
0
void
RoutePolar::Initialise(const GlideSettings &settings, const GlidePolar& polar,
                       const SpeedVector& wind,
                       const bool is_glide)
{
  static constexpr Angle ang_step = Angle::FullCircle() / ROUTEPOLAR_POINTS;

  Angle ang = Angle::QuarterCircle();
  for (unsigned i = 0; i < ROUTEPOLAR_POINTS; ++i, ang -= ang_step) {
    GlideResult res = SolveTask(settings, polar, wind, ang, is_glide);
    if (res.IsOk()) {
      RoutePolarPoint point(res.time_elapsed, res.height_glide);
      points[i] = point;
    } else
      points[i].valid = false;
  }
}
Example #7
0
fixed
TaskSolveTravelled::time_error()
{
  GlideResult res = tm.glide_solution(aircraft);
  if (!res.IsOk())
    /* what can we do if there's no solution?  This is an attempt to
       make ZeroFinder ignore this call, by returning a large value.
       I'm not sure if this kludge is correct. */
    return fixed(999999);

#ifdef SOLVE_ZERO
  fixed d = res.time_elapsed-dt;
#else
  fixed d = fabs(res.time_elapsed-dt);
#endif
  d += res.time_virtual;

  return d*inv_dt;
}
Example #8
0
void
CrossSectionRenderer::PaintGlide(ChartRenderer &chart) const
{
  if (!gps_info.NavAltitudeAvailable() || !glide_polar.IsValid())
    return;

  const fixed altitude = gps_info.nav_altitude;

  const MacCready mc(glide_settings, glide_polar);
  const GlideState task(vec, fixed(0), altitude,
                        calculated_info.GetWindOrZero());
  const GlideResult result = mc.SolveStraight(task);
  if (!result.IsOk())
    return;

  chart.DrawLine(fixed(0), altitude, result.vector.distance,
                 result.GetArrivalAltitude(),
                 ChartLook::STYLE_BLUETHIN);
}
Example #9
0
  void CalculateReachabilityDirect(const MoreData &basic,
                                   const SpeedVector &wind,
                                   const MacCready &mac_cready,
                                   const TaskBehaviour &task_behaviour) {
    assert(basic.location_available);
    assert(basic.NavAltitudeAvailable());

    const auto elevation = waypoint->elevation +
      task_behaviour.safety_height_arrival;
    const GlideState state(GeoVector(basic.location, waypoint->location),
                           elevation, basic.nav_altitude, wind);

    const GlideResult result = mac_cready.SolveStraight(state);
    if (!result.IsOk())
      return;

    reach.direct = result.pure_glide_altitude_difference;
    if (result.pure_glide_altitude_difference > 0)
      reachable = WaypointRenderer::ReachableTerrain;
  }
 /**
  * Specialisation of AirspaceAircraftPerformance for tasks where
  * part of the path is in cruise, part in final glide.  This is
  * intended to be used temporarily only.
  *
  * This simplifies the path by assuming flight is constant altitude
  * or descent to the task point elevation.
  */
 AirspaceAircraftPerformance(const GlidePolar &polar,
                             const GlideResult &solution)
   :vertical_tolerance(0.001),
    cruise_speed(positive(solution.time_elapsed)
                 ? solution.vector.distance / solution.time_elapsed
                 : fixed(1)),
    cruise_descent(positive(solution.time_elapsed)
                   ? (positive(solution.height_climb)
                      ? -solution.height_climb
                      : solution.height_glide) / solution.time_elapsed
                   : fixed(0)),
    descent_rate(polar.GetSBestLD()),
    climb_rate(positive(solution.time_elapsed) &&
               positive(solution.height_climb)
               ? polar.GetMC()
               : fixed(0)),
    max_speed(cruise_speed) {
   assert(polar.IsValid());
   assert(solution.IsOk());
   assert(solution.IsAchievable());
 }