//------------------------------------------------------------------------------ // Locates an elevation value (meters) for a given reference point and returns // it in 'elev'. Function returns true if successful, otherwise 'elev' is unchanged. //------------------------------------------------------------------------------ bool QuadMap::getElevation( LCreal* const elev, // The elevation value (meters) const double lat, // Reference latitude (degs) const double lon, // Reference longitude (degs) const bool interp // Interpolate between elevation posts (if true) ) const { // Early out tests if ( !isDataLoaded() || // Not loaded or (lat < getLatitudeSW() || lat > getLatitudeNE()) || // wrong latitude or (lon < getLongitudeSW() || lon > getLongitudeNE()) // wrong longitude ) return false; LCreal value = 0.0; // the elevation (meters) bool found = false; for (unsigned int i = 0; i < numDataFiles && !found; i++) { found = dataFiles[i]->getElevation(&value, lat, lon, interp); } if (found) { *elev = value; } return found; }
//------------------------------------------------------------------------------ // Computes the nearest row index for the latitude (degs). // Returns true if the index is valid //------------------------------------------------------------------------------ bool DataFile::computerRowIndex(unsigned int* const irow, const double lat) const { // Early out tests if ( (lat < getLatitudeSW() || lat > getLatitudeNE()) || // the latitude's out of range, or (irow == 0) || // the 'irow' pointer wasn't provided, or !isDataLoaded() // the data isn't loaded ) return false; // Locate row (latitude) index double points = (lat - getLatitudeSW()) / latSpacing; if (points < 0) points = 0; unsigned int idx = static_cast<unsigned int>(points + 0.5); if (idx >= nptlat) idx = (nptlat-1); *irow = idx; return true; }
//------------------------------------------------------------------------------ // Locates an elevation value (meters) for a given reference point and returns // it in 'elev'. Function returns true if successful, otherwise 'elev' is unchanged. //------------------------------------------------------------------------------ bool DataFile::getElevation( LCreal* const elev, // The elevation value (meters) const double lat, // Reference latitude (degs) const double lon, // Reference longitude (degs) const bool interp // Interpolate between elevation posts (if true) ) const { LCreal value = 0; // the elevation (meters) // Early out tests if ( !isDataLoaded() || // Not loaded or (lat < getLatitudeSW() || lat > getLatitudeNE()) || // wrong latitude or (lon < getLongitudeSW() || lon > getLongitudeNE()) // wrong longitude ) return false; // --- // Compute the lat and lon points // --- double pointsLat = (lat - getLatitudeSW()) / latSpacing; if (pointsLat < 0) pointsLat = 0; double pointsLon = (lon - getLongitudeSW()) / lonSpacing; if (pointsLon < 0) pointsLon = 0; // --- // Interpolating between elevation posts? // --- if (interp) { // Yes --- // South-west corner post is [icol][irow] unsigned int irow = static_cast<unsigned int>(pointsLat); unsigned int icol = static_cast<unsigned int>(pointsLon); if (irow > (nptlat-2)) irow = (nptlat-2); if (icol > (nptlong-2)) icol = (nptlong-2); // delta from s-w corner post LCreal deltaLat = static_cast<LCreal>(pointsLat - static_cast<double>(irow)); LCreal deltaLon = static_cast<LCreal>(pointsLon - static_cast<double>(icol)); // Get the elevations at each corner LCreal elevSW = static_cast<LCreal>(columns[icol][irow]); LCreal elevNW = static_cast<LCreal>(columns[icol][irow+1]); LCreal elevSE = static_cast<LCreal>(columns[icol+1][irow]); LCreal elevNE = static_cast<LCreal>(columns[icol+1][irow+1]); // Interpolate the west point LCreal westPoint = elevSW + (elevNW - elevSW) * deltaLat; // Interpolate the east point LCreal eastPoint = elevSE + (elevNE - elevSE) * deltaLat; // Interpolate between the west and east points value = westPoint + (eastPoint - westPoint) * deltaLon; } else { // No -- just use the nearest post // Nearest post unsigned int irow = static_cast<unsigned int>(pointsLat + 0.5f); unsigned int icol = static_cast<unsigned int>(pointsLon + 0.5f); if (irow >= nptlat) irow = (nptlat-1); if (icol >= nptlong) icol = (nptlong-1); // Get the elevation post at the current indices. value = static_cast<LCreal>(columns[icol][irow]); } // --- // Return the elevation value to the user // --- *elev = value; return true; }