void update( double t ) { osg::Vec3d pos; GeoMath::interpolate( _startLat.as(Units::RADIANS), _startLon.as(Units::RADIANS), _endLat.as(Units::RADIANS), _endLon.as(Units::RADIANS), t, pos.y(), pos.x() ); GeoPoint geo( _track->getMapNode()->getMapSRS(), osg::RadiansToDegrees(pos.x()), osg::RadiansToDegrees(pos.y()), 10000.0, ALTMODE_ABSOLUTE); // update the position label. _track->setPosition(geo); if ( g_showCoords ) { _track->setFieldValue( FIELD_POSITION, s_format(geo) ); } else _track->setFieldValue( FIELD_POSITION, "" ); }
bool LatLongFormatter::parseAngle( const std::string& input, Angular& out_value ) { const char* c = input.c_str(); double d=0.0, m=0.0, s=0.0; if (sscanf(c, "%lf:%lf:%lf", &d, &m, &s) == 3 || sscanf(c, "%lf\xb0%lf'%lf\"", &d, &m, &s) == 3 || sscanf(c, "%lf\xb0 %lf' %lf\"", &d, &m ,&s) == 3 || sscanf(c, "%lfd %lf' %lf\"", &d, &m, &s) == 3 || sscanf(c, "%lfd %lfm %lfs", &d, &m, &s) == 3 || sscanf(c, "%lf %lf' %lf\"", &d, &m, &s) == 3 ) { out_value.set( d + m/60.0 + s/3600.0, Units::DEGREES ); return true; } else if ( sscanf(c, "%lf:%lf", &d, &m) == 2 || sscanf(c, "%lf\xb0 %lf'", &d, &m) == 2 || sscanf(c, "%lf\xb0%lf'", &d, &m) == 2 || sscanf(c, "%lfd %lf'", &d, &m) == 2 || sscanf(c, "%lfd %lfm", &d, &m) == 2 || sscanf(c, "%lfd%lf'", &d, &m) == 2 || sscanf(c, "%lf %lf'", &d, &m) == 2 ) { out_value.set( d + m/60.0, Units::DEGREES ); return true; } else if ( sscanf(c, "%lf\xb0", &d) == 1 || sscanf(c, "%lfd", &d) == 1 || sscanf(c, "%lf", &d) == 1 ) { out_value.set( d, Units::DEGREES ); return true; } return false; }
void ImageOverlay::setBoundsAndRotation(const osgEarth::Bounds& b, const Angular& rot) { double rot_rad = rot.as(Units::RADIANS); if ( osg::equivalent( rot_rad, 0.0 ) ) { setBounds( b ); } else { osg::Vec3d ll( b.xMin(), b.yMin(), 0 ); osg::Vec3d ul( b.xMin(), b.yMax(), 0 ); osg::Vec3d ur( b.xMax(), b.yMax(), 0 ); osg::Vec3d lr( b.xMax(), b.yMin(), 0 ); double sinR = sin(-rot_rad), cosR = cos(-rot_rad); osg::Vec3d c( 0.5*(b.xMax()+b.xMin()), 0.5*(b.yMax()+b.yMin()), 0); // there must be a better way, but my internet is down so i can't look it up with now.. osg::ref_ptr<const SpatialReference> srs = SpatialReference::create("wgs84"); osg::ref_ptr<const SpatialReference> utm = srs->createUTMFromLonLat( c.x(), c.y() ); osg::Vec3d ll_utm, ul_utm, ur_utm, lr_utm, c_utm; srs->transform( ll, utm.get(), ll_utm ); srs->transform( ul, utm.get(), ul_utm ); srs->transform( ur, utm.get(), ur_utm ); srs->transform( lr, utm.get(), lr_utm ); srs->transform( c, utm.get(), c_utm ); osg::Vec3d llp( cosR*(ll_utm.x()-c_utm.x()) - sinR*(ll_utm.y()-c_utm.y()), sinR*(ll_utm.x()-c_utm.x()) + cosR*(ll_utm.y()-c_utm.y()), 0 ); osg::Vec3d ulp( cosR*(ul_utm.x()-c_utm.x()) - sinR*(ul_utm.y()-c_utm.y()), sinR*(ul_utm.x()-c_utm.x()) + cosR*(ul_utm.y()-c_utm.y()), 0 ); osg::Vec3d urp( cosR*(ur_utm.x()-c_utm.x()) - sinR*(ur_utm.y()-c_utm.y()), sinR*(ur_utm.x()-c_utm.x()) + cosR*(ur_utm.y()-c_utm.y()), 0 ); osg::Vec3d lrp( cosR*(lr_utm.x()-c_utm.x()) - sinR*(lr_utm.y()-c_utm.y()), sinR*(lr_utm.x()-c_utm.x()) + cosR*(lr_utm.y()-c_utm.y()), 0 ); utm->transform( (llp+c_utm), srs.get(), ll ); utm->transform( (ulp+c_utm), srs.get(), ul ); utm->transform( (urp+c_utm), srs.get(), ur ); utm->transform( (lrp+c_utm), srs.get(), lr ); setCorners( osg::Vec2d(ll.x(), ll.y()), osg::Vec2d(lr.x(), lr.y()), osg::Vec2d(ul.x(), ul.y()), osg::Vec2d(ur.x(), ur.y()) ); } }
std::string LatLongFormatter::format( const Angular& angle, int precision, const AngularFormat& format ) const { std::stringstream buf; std::string result; std::string space = _options & USE_SPACES ? " " : ""; AngularFormat f = format == FORMAT_DEFAULT ? _defaultFormat : format; if ( precision < 0 ) precision = _prec; if ( precision > 0 ) buf << std::setprecision(precision); double df = angle.as(Units::DEGREES); while( df < -180. ) df += 360.; while( df > 180. ) df -= 360.; switch( f ) { case FORMAT_DECIMAL_DEGREES: { if ( _options & USE_SYMBOLS ) buf << df << "\xb0"; else buf << df; } break; case FORMAT_DEGREES_DECIMAL_MINUTES: { int d = (int)floor(df); double mf = 60.0*(df-(double)d); if ( mf == 60.0 ) { d += 1; mf = 0.0; } if ( _options & USE_SYMBOLS ) buf << d << "\xb0" << space << mf << "'"; else if ( _options & USE_COLONS ) buf << d << ":" << mf; else buf << d << " " << mf; } break; case FORMAT_DEGREES_MINUTES_SECONDS: { int d = (int)floor(df); double mf = 60.0*(df-(double)d); int m = (int)floor(mf); double sf = 60.0*(mf-(double)m); if ( sf == 60.0 ) { m += 1; sf = 0.0; if ( m == 60 ) { d += 1; m = 0; } } if ( _options & USE_SYMBOLS ) buf << d << "\xb0" << space << m << "'" << space << sf << "\""; else if ( _options & USE_COLONS ) buf << d << ":" << m << ":" << sf; else buf << d << " " << m << " " << sf; } break; } result = buf.str(); return result; }
std::string LatLongFormatter::format( const Angular& angle, bool latitude, int precision, const AngularFormat& format ) const { std::stringstream buf; std::string result; std::string space = _options & USE_SPACES ? " " : ""; AngularFormat f = format == FORMAT_DEFAULT ? _defaultFormat : format; if ( precision < 0 ) precision = _prec; if ( precision > 0 ) buf << std::setprecision(precision); double df = angle.as(Units::DEGREES); while( df < -180. ) df += 360.; while( df > 180. ) df -= 360.; // Determine the label to use for suffixes or prefixes std::string label; if (latitude) { label = df < 0 ? "S":"N"; } else { label = df < 0 ? "W":"E"; } std::string prefix = ""; std::string suffix = ""; bool makePositive = false; if (_options & USE_PREFIXES) { prefix = label; makePositive = true; } else if (_options & USE_SUFFIXES) { suffix = label; makePositive = true; } // If we are using suffixes or prefixes then make the value positive. if (makePositive) { df = osg::absolute(df); } switch( f ) { case FORMAT_DECIMAL_DEGREES: { if ( _options & USE_SYMBOLS ) buf << prefix << df << "\xb0" << suffix; else buf << prefix << df << suffix; } break; case FORMAT_DEGREES_DECIMAL_MINUTES: { int d = (int)floor(df); double mf = 60.0*(df-(double)d); if ( mf == 60.0 ) { d += 1; mf = 0.0; } if ( _options & USE_SYMBOLS ) buf << prefix << d << "\xb0" << space << mf << "'" << suffix; else if ( _options & USE_COLONS ) buf << prefix << d << ":" << mf << suffix; else buf << prefix << d << " " << mf << suffix; } break; case FORMAT_DEGREES_MINUTES_SECONDS: { int d = (int)floor(df); double mf = 60.0*(df-(double)d); int m = (int)floor(mf); double sf = 60.0*(mf-(double)m); if ( sf == 60.0 ) { m += 1; sf = 0.0; if ( m == 60 ) { d += 1; m = 0; } } if ( _options & USE_SYMBOLS ) { buf << prefix << d << "\xb0" << space << m << "'" << space << sf << "\"" << suffix; } else if ( _options & USE_COLONS ) buf << prefix << d << ":" << m << ":" << sf << suffix; else buf << prefix << d << " " << m << " " << sf << suffix; } break; case FORMAT_DEGREES_MINUTES_SECONDS_TERSE: { int d = (int)floor(df); double mf = 60.0*(df-(double)d); int m = (int)floor(mf); double sf = 60.0*(mf-(double)m); int s = osg::round(sf); if ( s == 60 ) { m += 1; s = 0; if ( m == 60 ) { d += 1; m = 0; } } if ( _options & USE_SYMBOLS ) { buf << prefix << d << "\xb0"; if (m != 0 || s != 0) { buf << space << m << "'"; if (s != 0) { buf << space << s << "\"" << suffix; } } buf << suffix; } else if ( _options & USE_COLONS ) { buf << prefix << d; if (m != 0 || s != 0) { buf << ":" << m; if (s != 0) { buf << ":" << s; } } buf << suffix; } else { buf << prefix << d; if (m != 0 || s != 0) { buf << " " << m; if (s != 0) { buf << " " << s; } } buf << suffix; } } break; case FORMAT_DEFAULT: default: break; } result = buf.str(); return result; }