![]() |
VR-Forces 4.0.4 Class Documentation
|
This example shows how to create and install a new Coordinate Display through a plugin.
It implements the abstract class DtCoordinateDisplay to provide for the display of coordinates in the Swiss National Grid (CH1903) coordinate system.
The file exampleCoordinateDisplayPlugin.h sets up the necessary DLL export macros
#ifdef _WIN32 #ifdef EXAMPLECOORDINATEDISPLAYPLUGIN_EXPORTS #define DT_DLL_EXAMPLECOORDINATEDISPLAYPLUGIN __declspec ( dllexport ) #else #define DT_DLL_EXAMPLECOORDINATEDISPLAYPLUGIN __declspec ( dllimport ) #endif #else #define DT_DLL_EXAMPLECOORDINATEDISPLAYPLUGIN #endif #define DT_DE_PLUGIN_EXPORT_MACRO DT_DLL_EXAMPLECOORDINATEDISPLAYPLUGIN
The file exampleCoordinateDisplayPluginInit.cxx contains the implementation of the methods needed to initialize the plugin.
initDeModule is the method that will be called to initialize the plugin. It calls the init function and simply returns true.
// Declare & export the plugin initialization function (bool initDeModule(DtDe* de)) #include <vrvCore/exportPlugin.h> #include "sngDisplay.h" #include <vrvCore/DtDe.h> #include <vrvCore/DtDeSharedState.h> #include <vrvUtil/DtCoordinateDisplayCollection.h> #include <vrvUtil/DtCoordinateSystem.h> using namespace makVrv; namespace vrvExampleCoordinateDisplayPlugin { void installCoordinateDisplay(DtDe& de) { de.sharedState().coordinateSystem().displays().addCoordinateDisplay( SngCoordinateDisplay::CoordSysSNG, new SngCoordinateDisplay( de.sharedState().coordinateSystem() ) ); }
The init method does the plugin initialization.
void init(DtDe& de)
DT_DE_INIT_ONCE(de);
It then checks to make sure the plugin is only initialized for master display engines:
if (de.isInMasterMode())
Provided it is a master display engine, it connects the installCoordinateDisplay method to the display engine's signal_initializeDefaultState, which will be raised after the display engine's shared state has been initialized (a prerequisite for installing the coordinate display):
de.signal_initializeDefaultState.connect(boost::bind(
&installCoordinateDisplay, boost::ref(de) ));
The installCoordinateDisplay function installs an SngCoordinateDisplayObject.
void installCoordinateDisplay(DtDe& de)
It creates an instance of an SngCoordinateDisplay and adds it to the coordinate system's list of coordinate display objects:
de.sharedState().coordinateSystem().displays().addCoordinateDisplay(
SngCoordinateDisplay::CoordSysSNG,
new SngCoordinateDisplay( de.sharedState().coordinateSystem() ) );
sngDisplay.h contains the declaration of the SngCoordinateDisplay class.
SngCoordinateDisplay inherits from makVrv::DtCoordinateDisplay:class SngCoordinateDisplay : public makVrv::DtCoordinateDisplay
It defines a static constant to provide a numerical identifier to the type of coordinate system it displays. Note that this must be unique. In the example, we use the first available user-defined value:
Declarations are provided to override the following DtCoordinateDisplay methods:
DistanceUnits xUnitsFor(DistanceUnits unit ); DistanceUnits yUnitsFor(DistanceUnits unit ); DistanceUnits zUnitsFor( DistanceUnits unit ); virtual makVrv::DtUnicode xAxisLabel(); virtual makVrv::DtUnicode yAxisLabel(); virtual makVrv::DtUnicode zAxisLabel(); virtual makVrv::DtUnicode northSouthGridLabel( DistanceUnits unit, const DtVector& geocPos, int decimals, double gridSpacing ); virtual makVrv::DtUnicode eastWestGridLabel( DistanceUnits unit, const DtVector& geocPos, int decimals, double gridSpacing ); virtual std::vector<std::string> convertPositionToStringList( DistanceUnits unit, const DtVector& geocPos, int decimals); virtual void convertToGeocentric( const std::string& x, const std::string& y, const std::string& z, DistanceUnits distUnits, DistanceUnits altUnits, DtVector& vector); virtual makVrv::DtUnicode name(); virtual makVrv::DtCoordinateDisplay* clone() const; DtVector convertFromGeocentric( const DtVector& geoc ) const; DtTaitBryan headingPitchRollFor( const DtVector& location, const DtTaitBryan& geocOri ) const; DtTaitBryan localOrientationFor( const DtVector& location, const DtTaitBryan& geocOri ) const; DtTaitBryan orientationFor( const DtVector& location, const DtTaitBryan& geocOri, bool local ) const; void regularExpressionValidator( std::string& x, std::string& y, std::string& z );
Two protected methods unique to the class are provided for converting between SNG and WGS84 coordinates:
static void convertWGS84ToSNG(const DtVector& InVector, DtVector& OutVector); static void convertSNGToWGS84(const DtVector& InVecPos, DtVector& OutVecPos );
sngDisplay.cxx contains the implementation of these methods.
VR-Vantage includes pre-built versions of the example plug-in. To build it yourself, follow the instructions at Building VR-Vantage Examples, Applications, and Plug-ins.
This example is a plug-in. You can run it by running ./bin/exampleCoordinateDisplay_stealth.bat (on Windows) or ./bin/exampleCoordinateDisplay_stealth.sh (on Linux). For more information about running examples, please see Running Applications and Examples.
/****************************************************************************** ** Copyright (c) 2011 MAK Technologies, Inc. ** All rights reserved. ******************************************************************************/ /****************************************************************************** ** $RCSfile: exampleCoordinateDisplayPlugin.h,v $ $Revision: 1.1 $ $State: Exp $ ******************************************************************************/ #pragma once #ifdef _WIN32 #ifdef EXAMPLECOORDINATEDISPLAYPLUGIN_EXPORTS #define DT_DLL_EXAMPLECOORDINATEDISPLAYPLUGIN __declspec ( dllexport ) #else #define DT_DLL_EXAMPLECOORDINATEDISPLAYPLUGIN __declspec ( dllimport ) #endif #else #define DT_DLL_EXAMPLECOORDINATEDISPLAYPLUGIN #endif #define DT_DE_PLUGIN_EXPORT_MACRO DT_DLL_EXAMPLECOORDINATEDISPLAYPLUGIN
/****************************************************************************** ** Copyright (c) 2011 MAK Technologies, Inc. ** All rights reserved. ******************************************************************************/ /****************************************************************************** ** $RCSfile: exampleCoordinateDisplayPlugin.cxx,v $ $Revision: 1.1 $ $State: Exp $ ******************************************************************************/ #include "exampleCoordinateDisplayPlugin.h" // Declare & export the plugin initialization function (bool initDeModule(DtDe* de)) #include <vrvCore/exportPlugin.h> #include "sngDisplay.h" #include <vrvCore/DtDe.h> #include <vrvCore/DtDeSharedState.h> #include <vrvUtil/DtCoordinateDisplayCollection.h> #include <vrvUtil/DtCoordinateSystem.h> using namespace makVrv; namespace vrvExampleCoordinateDisplayPlugin { void installCoordinateDisplay(DtDe& de) { de.sharedState().coordinateSystem().displays().addCoordinateDisplay( SngCoordinateDisplay::CoordSysSNG, new SngCoordinateDisplay( de.sharedState().coordinateSystem() ) ); } void init(DtDe& de) { // Ensure that init only gets called once // (not strictly necessary here, but this is good practice in general) DT_DE_INIT_ONCE(de); // We only want to add the coordinate display if we are running in master mode. if (de.isInMasterMode()) { // The coordinate display must be created after the DE's initialization of // shared state is finished, but before any de observer announcements. de.signal_initializeDefaultState.connect(boost::bind( &installCoordinateDisplay, boost::ref(de) )); } } } bool initDeModule(makVrv::DtDe* de) { // Setup the plug-in. Normally, the init function and functionality // should be in its own library. vrvExampleCoordinateDisplayPlugin::init(*de); return true; }
/****************************************************************************** ** Copyright (c) 2011 MAK Technologies, Inc. ** All rights reserved. ******************************************************************************/ #include <vrvUtil/DtDatabaseCoordinateDisplay.h> class SngCoordinateDisplay : public makVrv::DtCoordinateDisplay { public: // Extend the CoordSys enumeration static const CoordSys CoordSysSNG = makArchives::DtDisplayUnitsSettingsRecord::CoordSysUserStart; SngCoordinateDisplay(const makVrv::DtCoordinateSystem& cs ); DistanceUnits xUnitsFor(DistanceUnits unit ); DistanceUnits yUnitsFor(DistanceUnits unit ); DistanceUnits zUnitsFor( DistanceUnits unit ); virtual makVrv::DtUnicode xAxisLabel(); virtual makVrv::DtUnicode yAxisLabel(); virtual makVrv::DtUnicode zAxisLabel(); virtual makVrv::DtUnicode northSouthGridLabel( DistanceUnits unit, const DtVector& geocPos, int decimals, double gridSpacing ); virtual makVrv::DtUnicode eastWestGridLabel( DistanceUnits unit, const DtVector& geocPos, int decimals, double gridSpacing ); virtual std::vector<std::string> convertPositionToStringList( DistanceUnits unit, const DtVector& geocPos, int decimals); virtual void convertToGeocentric( const std::string& x, const std::string& y, const std::string& z, DistanceUnits distUnits, DistanceUnits altUnits, DtVector& vector); virtual makVrv::DtUnicode name(); virtual makVrv::DtCoordinateDisplay* clone() const; DtVector convertFromGeocentric( const DtVector& geoc ) const; DtTaitBryan headingPitchRollFor( const DtVector& location, const DtTaitBryan& geocOri ) const; DtTaitBryan localOrientationFor( const DtVector& location, const DtTaitBryan& geocOri ) const; DtTaitBryan orientationFor( const DtVector& location, const DtTaitBryan& geocOri, bool local ) const; void regularExpressionValidator( std::string& x, std::string& y, std::string& z ); protected: static void convertWGS84ToSNG(const DtVector& InVector, DtVector& OutVector); static void convertSNGToWGS84(const DtVector& InVecPos, DtVector& OutVecPos ); };
/****************************************************************************** ** Copyright (c) 2011 MAK Technologies, Inc. ** All rights reserved. ******************************************************************************/ #include "sngDisplay.h" // Additional includes for the SNG Display #include <vrvUtil/DtDatabaseCoordinateDisplay.h> #include <vrvUtil/DtUnitConverterCollection.h> #include <vrvUtil/DtCoordinateSystem.h> #include <vrvUtil/DtCoordinateConverter.h> #include <vrvUtil/sprintfUtil.h> #include <matrix/vlTaitBryan.h> #ifdef __linux__ #include <stdio.h> #endif #define PI 3.14159265 #define RAD2DEG(x) (x * 180/PI) #define DEG2RAD(x) (x * PI/180) using namespace makVrv; SngCoordinateDisplay::SngCoordinateDisplay(const DtCoordinateSystem& cs) : DtCoordinateDisplay(cs) { addSupportedPositionUnit( makArchives::DtDisplayUnitsSettingsRecord::UnitsMeters ); addSupportedCSForGridLines( DtCoordinateConverter::FlatEarth ); } DtCoordinateDisplay* SngCoordinateDisplay::clone() const { return new SngCoordinateDisplay(myCoordinateSystem); } DtUnicode SngCoordinateDisplay::name() { return DtUnicode::tr("SNG System"); } DtUnicode SngCoordinateDisplay::xAxisLabel() { return DtUnicode::tr("E"); } DtUnicode SngCoordinateDisplay::yAxisLabel() { return DtUnicode::tr("N"); } DtUnicode SngCoordinateDisplay::zAxisLabel() { return DtUnicode::tr("Alt"); } DtUnicode SngCoordinateDisplay::eastWestGridLabel( makArchives::DtDisplayUnitsSettingsRecord::DistanceUnits unit, const DtVector& geocPos, int decimals, double gridSpacing ) { std::vector<std::string> lst = convertPositionToStringList( unit, geocPos, decimals ); return DtUnicode::fromAscii( lst[1] ); } DtUnicode SngCoordinateDisplay::northSouthGridLabel( makArchives::DtDisplayUnitsSettingsRecord::DistanceUnits unit, const DtVector& geocPos, int decimals, double gridSpacing ) { std::vector<std::string> lst = convertPositionToStringList( unit, geocPos, decimals ); return DtUnicode::fromAscii( lst[0] ); } std::vector<std::string> SngCoordinateDisplay::convertPositionToStringList( makArchives::DtDisplayUnitsSettingsRecord::DistanceUnits unit, const DtVector& geocPos, int decimals) { DtGeodeticCoord geodeticPosition; geodeticPosition.setGeocentric( geocPos ); DtVector InVector(RAD2DEG(geodeticPosition.lat()), RAD2DEG(geodeticPosition.lon()), geodeticPosition.alt()); DtVector OutVector; convertWGS84ToSNG(InVector, OutVector); const DtDistanceUnitConverter* altConverter = myCoordinateSystem.units().distanceConverterFor( zUnitsFor(unit) ); double alt = altConverter->metersToLocal( OutVector.z() ); char buffer[256]; std::vector<std::string> results; DtSnprintf( buffer, 256, "%.0f", OutVector.x() ); results.push_back( std::string(buffer) ); DtSnprintf( buffer, 256, "%.0f", OutVector.y() ); results.push_back( std::string(buffer) ); DtSnprintf( buffer, 256, "%.*f", decimals, alt ); results.push_back( std::string(buffer) ); return results; } void SngCoordinateDisplay::convertToGeocentric(const std::string& x, const std::string& y, const std::string& z, makArchives::DtDisplayUnitsSettingsRecord::DistanceUnits distUnits, makArchives::DtDisplayUnitsSettingsRecord::DistanceUnits altUnits, DtVector& vector) { const DtDistanceUnitConverter* distConverter = myCoordinateSystem.units().distanceConverterFor(distUnits); const DtDistanceUnitConverter* altConverter = myCoordinateSystem.units().distanceConverterFor(altUnits); DtVector InVector( distConverter->localToMeters( atof(x.c_str() ) ), distConverter->localToMeters( atof( y.c_str()) ), altConverter->localToMeters( atof( z.c_str() ) ) ); DtVector OutVector; convertSNGToWGS84(InVector, OutVector); DtGeodeticCoord geod; geod.setLat(DEG2RAD(OutVector.x())); geod.setLon(DEG2RAD(OutVector.y())); geod.setAlt(OutVector.z()); vector = geod.geocentric(); } void SngCoordinateDisplay::convertWGS84ToSNG( const DtVector& InVecPos, DtVector& OutVecPos ) { if ( InVecPos.x() == 0.0 && InVecPos.y() == 0.0 && InVecPos.z() == 0.0 ) { return; } double lamdaTag = ( InVecPos.y() * 3600 - 26782.5 ) / 10000.0; double lamdaTag2 = lamdaTag * lamdaTag; double lamdaTag3 = lamdaTag2 * lamdaTag; double phiTag = ( InVecPos.x() * 3600 - 169028.66 ) / 10000.0; double phiTag2 = phiTag * phiTag; double phiTag3 = phiTag2 * phiTag; OutVecPos.setY( 200147.07 + (308807.95 * phiTag) + (3745.25 * lamdaTag2) + (76.63 * phiTag2) - (194.56 * lamdaTag2 * phiTag) + (119.79 * phiTag3) ); OutVecPos.setX( 600072.37 + (211455.93 * lamdaTag) - (10938.51 * lamdaTag * phiTag) - (0.36 * lamdaTag * phiTag2) - (44.54 * lamdaTag3) ); OutVecPos.setZ(InVecPos.z() - 49.55 + (2.73 * lamdaTag) + (6.94 * phiTag) ); } void SngCoordinateDisplay::convertSNGToWGS84(const DtVector& InVecPos, DtVector& OutVecPos ) { if ( InVecPos.x() == 0.0 && InVecPos.y() == 0.0 && InVecPos.z() == 0.0 ) { return; } double yTag = ( InVecPos.x() - 600000 ) / 1000000; double yTag2 = yTag * yTag; double yTag3 = yTag2 * yTag; double xTag = ( InVecPos.y() - 200000 ) / 1000000; double xTag2 = xTag * xTag; double xTag3 = xTag2 * xTag; OutVecPos.setX(( 2.6779094 + (4.728992 * yTag) + (0.791484 * yTag * xTag ) + (0.1306 * yTag * xTag2) - (0.0436 * yTag3) ) * (100.0 / 36.0) ); OutVecPos.setY(( 16.9023892 + (3.238272 * xTag) - (0.270978 * yTag2) - (0.002528 * xTag2) - (0.0447 * yTag2 * xTag) - (0.0140 * xTag3) ) * (100.0/36.0) ); OutVecPos.setZ( InVecPos.z() + 49.55 - (12.60 * yTag) - (22.64 * xTag) ); } DtVector SngCoordinateDisplay::convertFromGeocentric( const DtVector& geoc ) const { DtVector localVec; myCoordinateSystem.netToLocalPos( geoc, localVec ); return localVec; } DtTaitBryan SngCoordinateDisplay::headingPitchRollFor( const DtVector& location, const DtTaitBryan& geocOri ) const { return orientationFor( location, geocOri, false ); } DtTaitBryan SngCoordinateDisplay::localOrientationFor( const DtVector& location, const DtTaitBryan& geocOri ) const { return orientationFor( location, geocOri, true ); } void SngCoordinateDisplay::regularExpressionValidator( std::string& x, std::string& y, std::string& z ) { x = "^-?[0-9]{1,9}\\.[0-9]{1,9}"; y = x; z = x; } DtTaitBryan SngCoordinateDisplay::orientationFor( const DtVector& location, const DtTaitBryan& geocOri, bool local ) const { DtVector localPos; DtTaitBryan localOri; myCoordinateSystem.netToLocalPos( location, localPos ); myCoordinateSystem.netToLocalOri( localPos, geocOri, localOri ); // Clamp to [0,2Pi] if ( localOri.psi() < 0 ) { localOri.setPsi( localOri.psi() + 2 * PI ); } return localOri; } SngCoordinateDisplay::DistanceUnits SngCoordinateDisplay::xUnitsFor( DistanceUnits unit ) { if ( isSupportedPositionUnit( unit ) ) { return unit; } return makArchives::DtDisplayUnitsSettingsRecord::UnitsMeters; } SngCoordinateDisplay::DistanceUnits SngCoordinateDisplay::yUnitsFor( DistanceUnits unit ) { if ( isSupportedPositionUnit( unit ) ) { return unit; } return makArchives::DtDisplayUnitsSettingsRecord::UnitsMeters; } SngCoordinateDisplay::DistanceUnits SngCoordinateDisplay::zUnitsFor( DistanceUnits unit ) { if ( isSupportedPositionUnit( unit ) ) { return unit; } return makArchives::DtDisplayUnitsSettingsRecord::UnitsMeters; }