Exemple #1
0
bool
WaypointReaderFS::ParseLine(const TCHAR* line, const unsigned linenum,
                              Waypoints &way_points)
{
  //$FormatGEO
  //ACONCAGU  S 32 39 12.00    W 070 00 42.00  6962  Aconcagua
  //BERGNEUS  N 51 03 07.02    E 007 42 22.02   488  Bergneustadt [A]
  //GOLDENGA  N 37 49 03.00    W 122 28 42.00   227  Golden Gate Bridge
  //REDSQUAR  N 55 45 15.00    E 037 37 12.00   123  Red Square
  //SYDNEYOP  S 33 51 25.02    E 151 12 54.96     5  Sydney Opera

  //$FormatUTM
  //Aconcagu 19H   0405124   6386692   6962  Aconcagua
  //Bergneus 32U   0409312   5656398    488  Bergneustadt [A]
  //Golden G 10S   0545914   4185695    227  Golden Gate Bridge
  //Red Squa 37U   0413390   6179582    123  Red Square
  //Sydney O 56H   0334898   6252272      5  Sydney Opera

  if (line[0] == '\0')
    return true;

  if (linenum == 0 &&
      _tcsstr(line, _T("$FormatUTM")) == line) {
    is_utm = true;
    return true;
  }

  if (line[0] == _T('$'))
    return true;

  // Determine the length of the line
  size_t len = _tcslen(line);
  // If less then 27 characters -> something is wrong -> cancel
  if (len < (is_utm ? 39 : 47))
    return false;

  GeoPoint location;
  if ((!is_utm && !ParseLocation(line + 10, location)) ||
      (is_utm && !ParseLocationUTM(line + 9, location)))
    return false;

  Waypoint new_waypoint(location);
  new_waypoint.file_num = file_num;
  new_waypoint.original_id = 0;

  if (!ParseString(line, new_waypoint.name, 8))
    return false;

  if (!ParseAltitude(line + (is_utm ? 32 : 41), new_waypoint.elevation) &&
      !CheckAltitude(new_waypoint))
    return false;

  // Description (Characters 35-44)
  if (len > (is_utm ? 38 : 47))
    ParseString(line + (is_utm ? 38 : 47), new_waypoint.comment);

  way_points.Append(new_waypoint);
  return true;
}
bool
WaypointReaderOzi::ParseLine(const TCHAR* line, const unsigned linenum,
                              Waypoints &way_points)
{
  if (line[0] == '\0')
    return true;

  // Ignore first four header lines
  if (linenum < 4)
    return true;

  TCHAR ctemp[255];
  const TCHAR *params[20];
  static constexpr unsigned int max_params = ARRAY_SIZE(params);
  size_t n_params;

  if (_tcslen(line) >= ARRAY_SIZE(ctemp))
    /* line too long for buffer */
    return false;

  // Get fields
  n_params = ExtractParameters(line, ctemp, params, max_params, true, _T('"'));

  // Check if the basic fields are provided
  if (n_params < 15)
    return false;

  GeoPoint location;
  // Latitude (e.g. 5115.900N)
  if (!ParseAngle(params[2], location.latitude))
    return false;

  // Longitude (e.g. 00715.900W)
  if (!ParseAngle(params[3], location.longitude))
    return false;

  location.Normalize(); // ensure longitude is within -180:180

  Waypoint new_waypoint(location);
  new_waypoint.file_num = file_num;

  long value;
  new_waypoint.original_id = (ParseNumber(params[0], value) ? value : 0);

  if (!ParseString(params[1], new_waypoint.name))
    return false;

  if (ParseNumber(params[14], value) && value != -777)
    new_waypoint.elevation = Units::ToSysUnit(fixed(value), Unit::FEET);
  else if (!CheckAltitude(new_waypoint))
    return false;

  // Description (Characters 35-44)
  ParseString(params[11], new_waypoint.comment);

  way_points.Append(std::move(new_waypoint));
  return true;
}
bool
WaypointReaderZander::ParseLine(const TCHAR* line, const unsigned linenum,
                              Waypoints &way_points)
{
  // If (end-of-file or comment)
  if (line[0] == '\0' || line[0] == 0x1a ||
      _tcsstr(line, _T("**")) == line ||
      _tcsstr(line, _T("*")) == line)
    // -> return without error condition
    return true;

  // Determine the length of the line
  size_t len = _tcslen(line);
  // If less then 34 characters -> something is wrong -> cancel
  if (len < 34)
    return false;

  GeoPoint location;

  // Latitude (Characters 13-20 // DDMMSS(N/S))
  if (!ParseAngle(line + 13, location.latitude, true))
    return false;

  // Longitude (Characters 21-29 // DDDMMSS(E/W))
  if (!ParseAngle(line + 21, location.longitude, false))
    return false;

  location.Normalize(); // ensure longitude is within -180:180

  Waypoint new_waypoint(location);
  new_waypoint.file_num = file_num;
  new_waypoint.original_id = 0;

  // Name (Characters 0-12)
  if (!ParseString(line, new_waypoint.name, 12))
    return false;

  // Altitude (Characters 30-34 // e.g. 1561 (in meters))
  /// @todo configurable behaviour
  if (!ParseAltitude(line + 30, new_waypoint.elevation) &&
      !CheckAltitude(new_waypoint))
    return false;

  // Description (Characters 35-44)
  if (len > 35)
    ParseString(line + 35, new_waypoint.comment, 9);

  // Flags (Characters 45-49)
  if (len < 46 || !ParseFlags(line + 45, new_waypoint))
    if (len < 36 || !ParseFlagsFromDescription(line + 35, new_waypoint))
      new_waypoint.flags.turn_point = true;

  way_points.Append(new_waypoint);
  return true;
}
bool
WaypointReaderBase::CheckAltitude(Waypoint &new_waypoint) const
{
  return CheckAltitude(new_waypoint, terrain);
}
bool
WaypointReaderCompeGPS::ParseLine(const TCHAR* line, const unsigned linenum,
                                  Waypoints &waypoints)
{
  /*
   * G  WGS 84
   * U  1
   * W  IT05FC A 46.9121939503ºN 11.9605922700°E 27-MAR-62 00:00:00 566.000000 Ahornach Sand, Ahornach LP, GS und HG
   * w  Waypoint,0,-1.0,16777215,255,0,0,7,,0.0,
   * W  IT05FB A 46.9260440931ºN 11.9676733017°E 27-MAR-62 00:00:00 1425.000000 Ahornach Sand, Ahornach SP, GS und HG
   * w  Waypoint,0,-1.0,16777215,255,0,0,7,,0.0,
   *
   * W ShortName 31T 318570 4657569 27-MAR-62 00:00:00 0 some Comments
   * W ShortName A 41.234234N 7.234424W 27-MAR-62 00:00:00 0 Comments
   */

  // Skip projection and file encoding information
  if (*line == _T('G') || *line == _T('B'))
    return true;

  // Check for format: UTM or LatLon
  if (*line == _T('U') && _tcsstr(line, _T("U  0")) == line) {
    is_utm = true;
    return true;
  }

  // Skip non-waypoint lines
  if (*line != _T('W'))
    return true;

  // Skip W indicator and whitespace
  line++;
  while (*line == _T(' '))
    line++;

  // Find next space delimiter, skip shortname
  const TCHAR *name = line;
  const TCHAR *space = _tcsstr(line, _T(" "));
  if (space == NULL)
    return false;

  unsigned name_length = space - line;
  if (name_length == 0)
    return false;

  line = space;
  while (*line == _T(' '))
    line++;

  // Parse location
  GeoPoint location;
  if ((!is_utm && !ParseLocation(line, location)) ||
      (is_utm && !ParseLocationUTM(line, location)))
    return false;

  // Skip whitespace
  while (*line == _T(' '))
    line++;

  // Skip unused date field
  line = _tcsstr(line, _T(" "));
  if (line == NULL)
    return false;

  line++;

  // Skip unused time field
  line = _tcsstr(line, _T(" "));
  if (line == NULL)
    return false;

  line++;

  // Create new waypoint instance
  Waypoint waypoint(location);
  waypoint.file_num = file_num;
  waypoint.original_id = 0;
  waypoint.name.assign(name, name_length);

  // Parse altitude
  if (!ParseAltitude(line, waypoint.elevation) &&
      !CheckAltitude(waypoint))
    return false;

  // Skip whitespace
  while (*line == _T(' '))
    line++;

  // Parse waypoint name
  waypoint.comment.assign(line);

  waypoints.Append(std::move(waypoint));
  return true;
}
Exemple #6
0
bool
WaypointReaderSeeYou::ParseLine(const TCHAR* line, const unsigned linenum,
                              Waypoints &waypoints)
{
  enum {
    iName = 0,
    iLatitude = 3,
    iLongitude = 4,
    iElevation = 5,
    iStyle = 6,
    iRWDir = 7,
    iRWLen = 8,
    iFrequency = 9,
    iDescription = 10,
  };

  if (linenum == 0)
    ignore_following = false;

  // If (end-of-file or comment)
  if (StringIsEmpty(line) ||
      StringStartsWith(line, _T("**")) ||
      StringStartsWith(line, _T("*")))
    // -> return without error condition
    return true;

  TCHAR ctemp[4096];
  if (_tcslen(line) >= ARRAY_SIZE(ctemp))
    /* line too long for buffer */
    return false;

  // Skip first line if it doesn't begin with a quotation character
  // (usually the field order line)
  if (linenum == 0 && line[0] != _T('\"'))
    return true;

  // If task marker is reached ignore all following lines
  if (_tcsstr(line, _T("-----Related Tasks-----")) == line)
    ignore_following = true;
  if (ignore_following)
    return true;

  // Get fields
  const TCHAR *params[20];
  size_t n_params = ExtractParameters(line, ctemp, params,
                                      ARRAY_SIZE(params), true, _T('"'));

  // Check if the basic fields are provided
  if (iName >= n_params ||
      iLatitude >= n_params ||
      iLongitude >= n_params)
    return false;

  Waypoint new_waypoint;

  // Latitude (e.g. 5115.900N)
  if (!ParseAngle(params[iLatitude], new_waypoint.location.latitude, true))
    return false;

  // Longitude (e.g. 00715.900W)
  if (!ParseAngle(params[iLongitude], new_waypoint.location.longitude, false))
    return false;

  new_waypoint.location.Normalize(); // ensure longitude is within -180:180

  new_waypoint.file_num = file_num;
  new_waypoint.original_id = 0;

  // Name (e.g. "Some Turnpoint")
  if (*params[iName] == _T('\0'))
    return false;
  new_waypoint.name = params[iName];

  // Elevation (e.g. 458.0m)
  /// @todo configurable behaviour
  if ((iElevation >= n_params ||
      !ParseAltitude(params[iElevation], new_waypoint.elevation)) &&
      !CheckAltitude(new_waypoint))
    return false;

  // Style (e.g. 5)
  if (iStyle < n_params)
    ParseStyle(params[iStyle], new_waypoint.type);

  new_waypoint.flags.turn_point = true;

  // Frequency & runway direction/length (for airports and landables)
  // and description (e.g. "Some Description")
  if (new_waypoint.IsLandable()) {
    if (iFrequency < n_params)
      new_waypoint.radio_frequency = RadioFrequency::Parse(params[iFrequency]);

    // Runway length (e.g. 546.0m)
    fixed rwlen = fixed_minus_one;
    if (iRWLen < n_params && ParseDistance(params[iRWLen], rwlen) &&
        positive(rwlen))
      new_waypoint.runway.SetLength(uround(rwlen));

    if (iRWDir < n_params && *params[iRWDir]) {
      TCHAR *end;
      int direction =_tcstol(params[iRWDir], &end, 10);
      if (end == params[iRWDir] || direction < 0 || direction > 360 ||
          (direction == 0 && !positive(rwlen)))
        direction = -1;
      else if (direction == 360)
        direction = 0;
      if (direction >= 0)
        new_waypoint.runway.SetDirectionDegrees(direction);
    }
  }

  if (iDescription < n_params)
    new_waypoint.comment = params[iDescription];

  waypoints.Append(new_waypoint);
  return true;
}
bool
WaypointReaderWinPilot::ParseLine(const TCHAR* line, const unsigned linenum,
                                  Waypoints &waypoints)
{
    TCHAR ctemp[4096];
    const TCHAR *params[20];
    static const unsigned int max_params = ARRAY_SIZE(params);
    static bool welt2000_format = false;
    size_t n_params;

    if (linenum == 0)
        welt2000_format = false;

    // If (end-of-file)
    if (line[0] == '\0' || line[0] == 0x1a)
        // -> return without error condition
        return true;

    // If comment
    if (line[0] == _T('*')) {
        if (linenum == 0)
            welt2000_format = (_tcsstr(line, _T("WRITTEN BY WELT2000")) != NULL);
        // -> return without error condition
        return true;
    }

    if (_tcslen(line) >= ARRAY_SIZE(ctemp))
        /* line too long for buffer */
        return false;

    GeoPoint location;

    // Get fields
    n_params = ExtractParameters(line, ctemp, params, max_params, true);
    if (n_params < 6)
        return false;

    // Latitude (e.g. 51:15.900N)
    if (!ParseAngle(params[1], location.latitude, true))
        return false;

    // Longitude (e.g. 00715.900W)
    if (!ParseAngle(params[2], location.longitude, false))
        return false;
    location.Normalize(); // ensure longitude is within -180:180

    Waypoint new_waypoint(location);
    new_waypoint.file_num = file_num;
    new_waypoint.original_id = _tcstoul(params[0], NULL, 0);

    // Name (e.g. KAMPLI)
    if (*params[5] == _T('\0'))
        return false;
    new_waypoint.name=params[5];

    // Altitude (e.g. 458M)
    /// @todo configurable behaviour
    if (!ParseAltitude(params[3], new_waypoint.altitude) &&
            !CheckAltitude(new_waypoint))
        return false;

    if (n_params > 6) {
        // Description (e.g. 119.750 Airport)
        new_waypoint.comment=params[6];
        if (welt2000_format)
            ParseRunwayDirection(params[6], new_waypoint.runway);
    }

    // Waypoint Flags (e.g. AT)
    ParseFlags(params[4], new_waypoint);

    waypoints.Append(new_waypoint);
    return true;
}