/** Packages an image layer as a TMS folder. */ int makeTMS( osg::ArgumentParser& args ) { osgDB::Registry::instance()->getReaderWriterForExtension("png"); osgDB::Registry::instance()->getReaderWriterForExtension("jpg"); osgDB::Registry::instance()->getReaderWriterForExtension("tiff"); //Read the min level unsigned int minLevel = 0; while (args.read("--min-level", minLevel)); //Read the max level unsigned int maxLevel = 5; while (args.read("--max-level", maxLevel)); std::vector< Bounds > bounds; // restrict packaging to user-specified bounds. double xmin=DBL_MAX, ymin=DBL_MAX, xmax=DBL_MIN, ymax=DBL_MIN; while (args.read("--bounds", xmin, ymin, xmax, ymax )) { Bounds b; b.xMin() = xmin, b.yMin() = ymin, b.xMax() = xmax, b.yMax() = ymax; bounds.push_back( b ); } std::string tileList; while (args.read( "--tiles", tileList ) ); bool verbose = args.read("--verbose"); unsigned int batchSize = 0; args.read("--batchsize", batchSize); // Read the concurrency level unsigned int concurrency = 0; args.read("-c", concurrency); args.read("--concurrency", concurrency); bool writeXML = true; // load up the map osg::ref_ptr<MapNode> mapNode = MapNode::load( args ); if( !mapNode.valid() ) return usage( "Failed to load a valid .earth file" ); // Read in an index shapefile std::string index; while (args.read("--index", index)) { //Open the feature source OGRFeatureOptions featureOpt; featureOpt.url() = index; osg::ref_ptr< FeatureSource > features = FeatureSourceFactory::create( featureOpt ); features->initialize(); features->getFeatureProfile(); osg::ref_ptr< FeatureCursor > cursor = features->createFeatureCursor(); while (cursor.valid() && cursor->hasMore()) { osg::ref_ptr< Feature > feature = cursor->nextFeature(); osgEarth::Bounds featureBounds = feature->getGeometry()->getBounds(); GeoExtent ext( feature->getSRS(), featureBounds ); ext = ext.transform( mapNode->getMapSRS() ); bounds.push_back( ext.bounds() ); } } // see if the user wants to override the type extension (imagery only) std::string extension; args.read( "--ext", extension ); // find a .earth file on the command line std::string earthFile = findArgumentWithExtension( args, ".earth" ); // folder to which to write the TMS archive. std::string rootFolder; if( !args.read( "--out", rootFolder ) ) rootFolder = Stringify() << earthFile << ".tms_repo"; // whether to overwrite existing tile files //TODO: Support bool overwrite = false; if( args.read( "--overwrite" ) ) overwrite = true; // write out an earth file std::string outEarth; args.read( "--out-earth", outEarth ); std::string dbOptions; args.read( "--db-options", dbOptions ); std::string::size_type n = 0; while( (n = dbOptions.find( '"', n )) != dbOptions.npos ) { dbOptions.erase( n, 1 ); } osg::ref_ptr<osgDB::Options> options = new osgDB::Options( dbOptions ); // whether to keep 'empty' tiles bool keepEmpties = args.read( "--keep-empties" ); //TODO: Single color bool continueSingleColor = args.read( "--continue-single-color" ); // elevation pixel depth unsigned elevationPixelDepth = 32; args.read( "--elevation-pixel-depth", elevationPixelDepth ); // create a folder for the output osgDB::makeDirectory( rootFolder ); if( !osgDB::fileExists( rootFolder ) ) return usage( "Failed to create root output folder" ); int imageLayerIndex = -1; args.read("--image", imageLayerIndex); int elevationLayerIndex = -1; args.read("--elevation", elevationLayerIndex); Map* map = mapNode->getMap(); osg::ref_ptr< TileVisitor > visitor; // If we are given a task file, load it up and create a new TileKeyListVisitor if (!tileList.empty()) { TaskList tasks( mapNode->getMap()->getProfile() ); tasks.load( tileList ); TileKeyListVisitor* v = new TileKeyListVisitor(); v->setKeys( tasks.getKeys() ); visitor = v; // This process is a lowly worker, and shouldn't write out the XML file. writeXML = false; } // If we dont' have a visitor create one. if (!visitor.valid()) { if (args.read("--mt")) { // Create a multithreaded visitor MultithreadedTileVisitor* v = new MultithreadedTileVisitor(); if (concurrency > 0) { v->setNumThreads(concurrency); } visitor = v; } else if (args.read("--mp")) { // Create a multiprocess visitor MultiprocessTileVisitor* v = new MultiprocessTileVisitor(); if (concurrency > 0) { v->setNumProcesses(concurrency); OE_NOTICE << "Set num processes " << concurrency << std::endl; } if (batchSize > 0) { v->setBatchSize(batchSize); } // Try to find the earth file std::string earthFile; for(int pos=1;pos<args.argc();++pos) { if (!args.isOption(pos)) { earthFile = args[ pos ]; break; } } v->setEarthFile( earthFile ); visitor = v; } else { // Create a single thread visitor visitor = new TileVisitor(); } } osg::ref_ptr< ProgressCallback > progress = new ConsoleProgressCallback(); if (verbose) { visitor->setProgressCallback( progress ); } visitor->setMinLevel( minLevel ); visitor->setMaxLevel( maxLevel ); for (unsigned int i = 0; i < bounds.size(); i++) { GeoExtent extent(mapNode->getMapSRS(), bounds[i]); OE_DEBUG << "Adding extent " << extent.toString() << std::endl; visitor->addExtent( extent ); } // Setup a TMSPackager with all the options. TMSPackager packager; packager.setExtension(extension); packager.setVisitor(visitor); packager.setDestination(rootFolder); packager.setElevationPixelDepth(elevationPixelDepth); packager.setWriteOptions(options); packager.setOverwrite(overwrite); packager.setKeepEmpties(keepEmpties); // new map for an output earth file if necessary. osg::ref_ptr<Map> outMap = 0L; if( !outEarth.empty() ) { // copy the options from the source map first outMap = new Map( map->getInitialMapOptions() ); } std::string outEarthFile = osgDB::concatPaths( rootFolder, osgDB::getSimpleFileName( outEarth ) ); // Package an individual image layer if (imageLayerIndex >= 0) { ImageLayer* layer = map->getImageLayerAt(imageLayerIndex); if (layer) { packager.run(layer, map); if (writeXML) { packager.writeXML(layer, map); } } else { std::cout << "Failed to find an image layer at index " << imageLayerIndex << std::endl; return 1; } } // Package an individual elevation layer else if (elevationLayerIndex >= 0) { ElevationLayer* layer = map->getElevationLayerAt(elevationLayerIndex); if (layer) { packager.run(layer, map); if (writeXML) { packager.writeXML(layer, map ); } } else { std::cout << "Failed to find an elevation layer at index " << elevationLayerIndex << std::endl; return 1; } } else { // Package all the ImageLayer's for (unsigned int i = 0; i < map->getNumImageLayers(); i++) { ImageLayer* layer = map->getImageLayerAt(i); OE_NOTICE << "Packaging " << layer->getName() << std::endl; osg::Timer_t start = osg::Timer::instance()->tick(); packager.run(layer, map); osg::Timer_t end = osg::Timer::instance()->tick(); if (verbose) { OE_NOTICE << "Completed seeding layer " << layer->getName() << " in " << prettyPrintTime( osg::Timer::instance()->delta_s( start, end ) ) << std::endl; } if (writeXML) { packager.writeXML(layer, map); } // save to the output map if requested: if( outMap.valid() ) { std::string layerFolder = toLegalFileName( packager.getLayerName() ); // new TMS driver info: TMSOptions tms; tms.url() = URI( osgDB::concatPaths( layerFolder, "tms.xml" ), outEarthFile ); ImageLayerOptions layerOptions( packager.getLayerName(), tms ); layerOptions.mergeConfig( layer->getInitialOptions().getConfig( true ) ); layerOptions.cachePolicy() = CachePolicy::NO_CACHE; outMap->addImageLayer( new ImageLayer( layerOptions ) ); } } // Package all the ElevationLayer's for (unsigned int i = 0; i < map->getNumElevationLayers(); i++) { ElevationLayer* layer = map->getElevationLayerAt(i); OE_NOTICE << "Packaging " << layer->getName() << std::endl; osg::Timer_t start = osg::Timer::instance()->tick(); packager.run(layer, map); osg::Timer_t end = osg::Timer::instance()->tick(); if (verbose) { OE_NOTICE << "Completed seeding layer " << layer->getName() << " in " << prettyPrintTime( osg::Timer::instance()->delta_s( start, end ) ) << std::endl; } if (writeXML) { packager.writeXML(layer, map); } // save to the output map if requested: if( outMap.valid() ) { std::string layerFolder = toLegalFileName( packager.getLayerName() ); // new TMS driver info: TMSOptions tms; tms.url() = URI( osgDB::concatPaths( layerFolder, "tms.xml" ), outEarthFile ); ElevationLayerOptions layerOptions( packager.getLayerName(), tms ); layerOptions.mergeConfig( layer->getInitialOptions().getConfig( true ) ); layerOptions.cachePolicy() = CachePolicy::NO_CACHE; outMap->addElevationLayer( new ElevationLayer( layerOptions ) ); } } } // Write out an earth file if it was requested // Finally, write an earth file if requested: if( outMap.valid() ) { MapNodeOptions outNodeOptions = mapNode->getMapNodeOptions(); osg::ref_ptr<MapNode> outMapNode = new MapNode( outMap.get(), outNodeOptions ); if( !osgDB::writeNodeFile( *outMapNode.get(), outEarthFile ) ) { OE_WARN << LC << "Error writing earth file to \"" << outEarthFile << "\"" << std::endl; } else if( verbose ) { OE_NOTICE << LC << "Wrote earth file to \"" << outEarthFile << "\"" << std::endl; } } return 0; }
void MapNodeHelper::parse(MapNode* mapNode, osg::ArgumentParser& args, osgViewer::View* view, osg::Group* root, Control* userControl ) const { // this is a dubious move. if ( !root ) root = mapNode; // options to use for the load osg::ref_ptr<osgDB::Options> dbOptions = Registry::instance()->cloneOrCreateOptions(); // parse out custom example arguments first: bool useSky = args.read("--sky"); bool useOcean = args.read("--ocean"); bool useMGRS = args.read("--mgrs"); bool useDMS = args.read("--dms"); bool useDD = args.read("--dd"); bool useCoords = args.read("--coords") || useMGRS || useDMS || useDD; bool useOrtho = args.read("--ortho"); bool useAutoClip = args.read("--autoclip"); float ambientBrightness = 0.4f; args.read("--ambientBrightness", ambientBrightness); std::string kmlFile; args.read( "--kml", kmlFile ); std::string imageFolder; args.read( "--images", imageFolder ); std::string imageExtensions; args.read("--image-extensions", imageExtensions); // install a canvas for any UI controls we plan to create: ControlCanvas* canvas = ControlCanvas::get(view, false); Container* mainContainer = canvas->addControl( new VBox() ); mainContainer->setBackColor( Color(Color::Black, 0.8) ); mainContainer->setHorizAlign( Control::ALIGN_LEFT ); mainContainer->setVertAlign( Control::ALIGN_BOTTOM ); // install the user control: if ( userControl ) mainContainer->addControl( userControl ); // look for external data in the map node: const Config& externals = mapNode->externalConfig(); const Config& skyConf = externals.child("sky"); const Config& oceanConf = externals.child("ocean"); const Config& annoConf = externals.child("annotations"); const Config& declutterConf = externals.child("decluttering"); Config viewpointsConf = externals.child("viewpoints"); // backwards-compatibility: read viewpoints at the top level: const ConfigSet& old_viewpoints = externals.children("viewpoint"); for( ConfigSet::const_iterator i = old_viewpoints.begin(); i != old_viewpoints.end(); ++i ) viewpointsConf.add( *i ); // Loading a viewpoint list from the earth file: if ( !viewpointsConf.empty() ) { std::vector<Viewpoint> viewpoints; const ConfigSet& children = viewpointsConf.children(); if ( children.size() > 0 ) { for( ConfigSet::const_iterator i = children.begin(); i != children.end(); ++i ) { viewpoints.push_back( Viewpoint(*i) ); } } if ( viewpoints.size() > 0 ) { Control* c = ViewpointControlFactory().create(viewpoints, view); if ( c ) mainContainer->addControl( c ); } } // Adding a sky model: if ( useSky || !skyConf.empty() ) { double hours = skyConf.value( "hours", 12.0 ); SkyNode* sky = new SkyNode( mapNode->getMap() ); //sky->setAmbientBrightness( ambientBrightness ); sky->setAutoAmbience( true ); sky->setDateTime( 2011, 3, 6, hours ); sky->attach( view ); root->addChild( sky ); Control* c = SkyControlFactory().create(sky, view); if ( c ) mainContainer->addControl( c ); } // Adding an ocean model: if ( useOcean || !oceanConf.empty() ) { OceanSurfaceNode* ocean = new OceanSurfaceNode( mapNode, oceanConf ); if ( ocean ) { root->addChild( ocean ); Control* c = OceanControlFactory().create(ocean, view); if ( c ) mainContainer->addControl(c); } } // Loading KML from the command line: if ( !kmlFile.empty() ) { KMLOptions kml_options; kml_options.declutter() = true; // set up a default icon for point placemarks: IconSymbol* defaultIcon = new IconSymbol(); defaultIcon->url()->setLiteral(KML_PUSHPIN_URL); kml_options.defaultIconSymbol() = defaultIcon; osg::Node* kml = KML::load( URI(kmlFile), mapNode, kml_options ); if ( kml ) { Control* c = AnnotationGraphControlFactory().create(kml, view); if ( c ) { c->setVertAlign( Control::ALIGN_TOP ); canvas->addControl( c ); } root->addChild( kml ); } } // Annotations in the map node externals: if ( !annoConf.empty() ) { osg::Group* annotations = 0L; AnnotationRegistry::instance()->create( mapNode, annoConf, dbOptions.get(), annotations ); if ( annotations ) { root->addChild( annotations ); } } // Configure the de-cluttering engine for labels and annotations: if ( !declutterConf.empty() ) { Decluttering::setOptions( DeclutteringOptions(declutterConf) ); } // Configure the mouse coordinate readout: if ( useCoords ) { LabelControl* readout = new LabelControl(); readout->setBackColor( Color(Color::Black, 0.8) ); readout->setHorizAlign( Control::ALIGN_RIGHT ); readout->setVertAlign( Control::ALIGN_BOTTOM ); Formatter* formatter = useMGRS ? (Formatter*)new MGRSFormatter(MGRSFormatter::PRECISION_1M, 0L, MGRSFormatter::USE_SPACES) : useDMS ? (Formatter*)new LatLongFormatter(LatLongFormatter::FORMAT_DEGREES_MINUTES_SECONDS) : useDD ? (Formatter*)new LatLongFormatter(LatLongFormatter::FORMAT_DECIMAL_DEGREES) : 0L; MouseCoordsTool* mcTool = new MouseCoordsTool( mapNode ); mcTool->addCallback( new MouseCoordsLabelCallback(readout, formatter) ); view->addEventHandler( mcTool ); canvas->addControl( readout ); } // Configure for an ortho camera: if ( useOrtho ) { EarthManipulator* manip = dynamic_cast<EarthManipulator*>(view->getCameraManipulator()); if ( manip ) { manip->getSettings()->setCameraProjection( EarthManipulator::PROJ_ORTHOGRAPHIC ); } } // Install an auto clip plane clamper if ( useAutoClip ) { mapNode->addCullCallback( new AutoClipPlaneCullCallback(mapNode) ); } // Scan for images if necessary. if ( !imageFolder.empty() ) { std::vector<std::string> extensions; if ( !imageExtensions.empty() ) StringTokenizer( imageExtensions, extensions, ",;", "", false, true ); if ( extensions.empty() ) extensions.push_back( "tif" ); OE_INFO << LC << "Loading images from " << imageFolder << "..." << std::endl; ImageLayerVector imageLayers; DataScanner scanner; scanner.findImageLayers( imageFolder, extensions, imageLayers ); if ( imageLayers.size() > 0 ) { mapNode->getMap()->beginUpdate(); for( ImageLayerVector::iterator i = imageLayers.begin(); i != imageLayers.end(); ++i ) { mapNode->getMap()->addImageLayer( i->get() ); } mapNode->getMap()->endUpdate(); } OE_INFO << LC << "...found " << imageLayers.size() << " image layers." << std::endl; } // Generic named value uniform with min/max. VBox* uniformBox = 0L; while( args.find( "--uniform" ) >= 0 ) { std::string name; float minval, maxval; if ( args.read( "--uniform", name, minval, maxval ) ) { if ( uniformBox == 0L ) { uniformBox = new VBox(); uniformBox->setBackColor(0,0,0,0.5); uniformBox->setAbsorbEvents( true ); canvas->addControl( uniformBox ); } osg::Uniform* uniform = new osg::Uniform(osg::Uniform::FLOAT, name); uniform->set( minval ); root->getOrCreateStateSet()->addUniform( uniform, osg::StateAttribute::OVERRIDE ); HBox* box = new HBox(); box->addControl( new LabelControl(name) ); HSliderControl* hs = box->addControl( new HSliderControl(minval, maxval, minval, new ApplyValueUniform(uniform))); hs->setHorizFill(true, 200); box->addControl( new LabelControl(hs) ); uniformBox->addControl( box ); OE_INFO << LC << "Installed uniform controller for " << name << std::endl; } } root->addChild( canvas ); }
int seed( osg::ArgumentParser& args ) { osgDB::Registry::instance()->getReaderWriterForExtension("png"); osgDB::Registry::instance()->getReaderWriterForExtension("jpg"); osgDB::Registry::instance()->getReaderWriterForExtension("tiff"); //Read the min level int minLevel = -1; while (args.read("--min-level", minLevel)); //Read the max level int maxLevel = -1; while (args.read("--max-level", maxLevel)); bool estimate = args.read("--estimate"); std::vector< Bounds > bounds; // restrict packaging to user-specified bounds. double xmin=DBL_MAX, ymin=DBL_MAX, xmax=DBL_MIN, ymax=DBL_MIN; while (args.read("--bounds", xmin, ymin, xmax, ymax )) { Bounds b; b.xMin() = xmin, b.yMin() = ymin, b.xMax() = xmax, b.yMax() = ymax; bounds.push_back( b ); } std::string tileList; while (args.read( "--tiles", tileList ) ); bool verbose = args.read("--verbose"); unsigned int batchSize = 0; args.read("--batchsize", batchSize); // Read the concurrency level unsigned int concurrency = 0; args.read("-c", concurrency); args.read("--concurrency", concurrency); int imageLayerIndex = -1; args.read("--image", imageLayerIndex); int elevationLayerIndex = -1; args.read("--elevation", elevationLayerIndex); //Read in the earth file. osg::ref_ptr<osg::Node> node = osgDB::readNodeFiles( args ); if ( !node.valid() ) return usage( "Failed to read .earth file." ); MapNode* mapNode = MapNode::findMapNode( node.get() ); if ( !mapNode ) return usage( "Input file was not a .earth file" ); // Read in an index shapefile std::string index; while (args.read("--index", index)) { //Open the feature source OGRFeatureOptions featureOpt; featureOpt.url() = index; osg::ref_ptr< FeatureSource > features = FeatureSourceFactory::create( featureOpt ); Status status = features->open(); if (status.isOK()) { osg::ref_ptr< FeatureCursor > cursor = features->createFeatureCursor(0L); while (cursor.valid() && cursor->hasMore()) { osg::ref_ptr< Feature > feature = cursor->nextFeature(); osgEarth::Bounds featureBounds = feature->getGeometry()->getBounds(); GeoExtent ext( feature->getSRS(), featureBounds ); ext = ext.transform( mapNode->getMapSRS() ); bounds.push_back( ext.bounds() ); } } else { OE_WARN << status.message() << "\n"; } } // If they requested to do an estimate then don't do the seed, just print out the estimated values. if (estimate) { CacheEstimator est; if ( minLevel >= 0 ) est.setMinLevel( minLevel ); if ( maxLevel >= 0 ) est.setMaxLevel( maxLevel ); est.setProfile( mapNode->getMap()->getProfile() ); for (unsigned int i = 0; i < bounds.size(); i++) { GeoExtent extent(mapNode->getMapSRS(), bounds[i]); OE_DEBUG << "Adding extent " << extent.toString() << std::endl; est.addExtent( extent ); } unsigned int numTiles = est.getNumTiles(); double size = est.getSizeInMB(); double time = est.getTotalTimeInSeconds(); std::cout << "Cache Estimation " << std::endl << "---------------- " << std::endl << "Total number of tiles: " << numTiles << std::endl << "Size on disk: " << osgEarth::prettyPrintSize( size ) << std::endl << "Total time: " << osgEarth::prettyPrintTime( time ) << std::endl; return 0; } osg::ref_ptr< TileVisitor > visitor; // If we are given a task file, load it up and create a new TileKeyListVisitor if (!tileList.empty()) { TaskList tasks( mapNode->getMap()->getProfile() ); tasks.load( tileList ); TileKeyListVisitor* v = new TileKeyListVisitor(); v->setKeys( tasks.getKeys() ); visitor = v; OE_DEBUG << "Read task list with " << tasks.getKeys().size() << " tasks" << std::endl; } // If we dont' have a visitor create one. if (!visitor.valid()) { if (args.read("--mt")) { // Create a multithreaded visitor MultithreadedTileVisitor* v = new MultithreadedTileVisitor(); if (concurrency > 0) { v->setNumThreads(concurrency); } visitor = v; } else if (args.read("--mp")) { // Create a multiprocess visitor MultiprocessTileVisitor* v = new MultiprocessTileVisitor(); if (concurrency > 0) { v->setNumProcesses(concurrency); } if (batchSize > 0) { v->setBatchSize(batchSize); } // Try to find the earth file std::string earthFile; for(int pos=1;pos<args.argc();++pos) { if (!args.isOption(pos)) { earthFile = args[ pos ]; break; } } v->setEarthFile( earthFile ); visitor = v; } else { // Create a single thread visitor visitor = new TileVisitor(); } } osg::ref_ptr< ProgressCallback > progress = new ConsoleProgressCallback(); if (verbose) { visitor->setProgressCallback( progress.get() ); } if ( minLevel >= 0 ) visitor->setMinLevel( minLevel ); if ( maxLevel >= 0 ) visitor->setMaxLevel( maxLevel ); for (unsigned int i = 0; i < bounds.size(); i++) { GeoExtent extent(mapNode->getMapSRS(), bounds[i]); OE_DEBUG << "Adding extent " << extent.toString() << std::endl; visitor->addExtent( extent ); } // Initialize the seeder CacheSeed seeder; seeder.setVisitor(visitor.get()); osgEarth::Map* map = mapNode->getMap(); // They want to seed an image layer if (imageLayerIndex >= 0) { osg::ref_ptr< ImageLayer > layer = map->getLayerAt<ImageLayer>( imageLayerIndex ); if (layer) { OE_NOTICE << "Seeding single layer " << layer->getName() << std::endl; osg::Timer_t start = osg::Timer::instance()->tick(); seeder.run(layer.get(), map); osg::Timer_t end = osg::Timer::instance()->tick(); if (verbose) { OE_NOTICE << "Completed seeding layer " << layer->getName() << " in " << prettyPrintTime( osg::Timer::instance()->delta_s( start, end ) ) << std::endl; } } else { std::cout << "Failed to find an image layer at index " << imageLayerIndex << std::endl; return 1; } } // They want to seed an elevation layer else if (elevationLayerIndex >= 0) { osg::ref_ptr< ElevationLayer > layer = map->getLayerAt<ElevationLayer>( elevationLayerIndex ); if (layer) { OE_NOTICE << "Seeding single layer " << layer->getName() << std::endl; osg::Timer_t start = osg::Timer::instance()->tick(); seeder.run(layer.get(), map); osg::Timer_t end = osg::Timer::instance()->tick(); if (verbose) { OE_NOTICE << "Completed seeding layer " << layer->getName() << " in " << prettyPrintTime( osg::Timer::instance()->delta_s( start, end ) ) << std::endl; } } else { std::cout << "Failed to find an elevation layer at index " << elevationLayerIndex << std::endl; return 1; } } // They want to seed the entire map else { TerrainLayerVector terrainLayers; map->getLayers(terrainLayers); // Seed all the map layers for (unsigned int i = 0; i < terrainLayers.size(); ++i) { osg::ref_ptr< TerrainLayer > layer = terrainLayers[i].get(); OE_NOTICE << "Seeding layer" << layer->getName() << std::endl; osg::Timer_t start = osg::Timer::instance()->tick(); seeder.run(layer.get(), map); osg::Timer_t end = osg::Timer::instance()->tick(); if (verbose) { OE_NOTICE << "Completed seeding layer " << layer->getName() << " in " << prettyPrintTime( osg::Timer::instance()->delta_s( start, end ) ) << std::endl; } } //for (unsigned int i = 0; i < map->getNumElevationLayers(); ++i) //{ // osg::ref_ptr< ElevationLayer > layer = map->getElevationLayerAt(i); // OE_NOTICE << "Seeding layer" << layer->getName() << std::endl; // osg::Timer_t start = osg::Timer::instance()->tick(); // seeder.run(layer.get(), map); // osg::Timer_t end = osg::Timer::instance()->tick(); // if (verbose) // { // OE_NOTICE << "Completed seeding layer " << layer->getName() << " in " << prettyPrintTime( osg::Timer::instance()->delta_s( start, end ) ) << std::endl; // } //} } return 0; }
int mainAdapterWidget(QApplication& a, osg::ArgumentParser& arguments) { // load the scene. osg::ref_ptr<osg::Node> loadedModel = osgDB::readNodeFiles(arguments); if (!loadedModel) { std::cout << arguments[0] <<": No data loaded." << std::endl; return 1; } std::cout<<"Using AdapterWidget - QGLWidget subclassed to integrate with osgViewer using its embedded graphics window support."<<std::endl; if (arguments.read("--CompositeViewer")) { CompositeViewerQT* viewerWindow = new CompositeViewerQT; unsigned int width = viewerWindow->width(); unsigned int height = viewerWindow->height(); { osgViewer::View* view1 = new osgViewer::View; view1->getCamera()->setGraphicsContext(viewerWindow->getGraphicsWindow()); view1->getCamera()->setProjectionMatrixAsPerspective(30.0f, static_cast<double>(width)/static_cast<double>(height/2), 1.0, 1000.0); view1->getCamera()->setViewport(new osg::Viewport(0,0,width,height/2)); view1->setCameraManipulator(new osgGA::TrackballManipulator); view1->setSceneData(loadedModel.get()); viewerWindow->addView(view1); } { osgViewer::View* view2 = new osgViewer::View; view2->getCamera()->setGraphicsContext(viewerWindow->getGraphicsWindow()); view2->getCamera()->setProjectionMatrixAsPerspective(30.0f, static_cast<double>(width)/static_cast<double>(height/2), 1.0, 1000.0); view2->getCamera()->setViewport(new osg::Viewport(0,height/2,width,height/2)); view2->setCameraManipulator(new osgGA::TrackballManipulator); view2->setSceneData(loadedModel.get()); viewerWindow->addView(view2); } viewerWindow->show(); } else if (arguments.read("--mdi")) { std::cout<<"Using ViewetQT MDI version"<<std::endl; /* Following problems are found here: - miminize causes loaded model to disappear (some problem with Camera matrix? - clampProjectionMatrix is invalid) */ ViewerQT* viewerWindow = new ViewerQT; viewerWindow->setCameraManipulator(new osgGA::TrackballManipulator); viewerWindow->setSceneData(loadedModel.get()); QMainWindow* mw = new QMainWindow(); QMdiArea* mdiArea = new QMdiArea(mw); mw->setCentralWidget(mdiArea); QMdiSubWindow *subWindow = mdiArea->addSubWindow(viewerWindow); subWindow->showMaximized(); subWindow->setWindowTitle("New Window"); mw->show(); } else { ViewerQT* viewerWindow = new ViewerQT; viewerWindow->setCameraManipulator(new osgGA::TrackballManipulator); viewerWindow->setSceneData(loadedModel.get()); viewerWindow->show(); } a.connect( &a, SIGNAL(lastWindowClosed()), &a, SLOT(quit()) ); return a.exec(); }
void MapNodeHelper::parse(MapNode* mapNode, osg::ArgumentParser& args, osgViewer::View* view, osg::Group* root, Control* userControl ) const { if ( !root ) root = mapNode; // parse out custom example arguments first: bool useSky = args.read("--sky"); bool useOcean = args.read("--ocean"); bool useMGRS = args.read("--mgrs"); bool useDMS = args.read("--dms"); bool useDD = args.read("--dd"); bool useCoords = args.read("--coords") || useMGRS || useDMS || useDD; std::string kmlFile; args.read( "--kml", kmlFile ); // install a canvas for any UI controls we plan to create: ControlCanvas* canvas = ControlCanvas::get(view, false); Container* mainContainer = canvas->addControl( new VBox() ); mainContainer->setBackColor( Color(Color::Black, 0.8) ); mainContainer->setHorizAlign( Control::ALIGN_LEFT ); mainContainer->setVertAlign( Control::ALIGN_BOTTOM ); // install the user control: if ( userControl ) mainContainer->addControl( userControl ); // look for external data in the map node: const Config& externals = mapNode->externalConfig(); const Config& skyConf = externals.child("sky"); const Config& oceanConf = externals.child("ocean"); const Config& annoConf = externals.child("annotations"); const Config& declutterConf = externals.child("decluttering"); Config viewpointsConf = externals.child("viewpoints"); // backwards-compatibility: read viewpoints at the top level: const ConfigSet& old_viewpoints = externals.children("viewpoint"); for( ConfigSet::const_iterator i = old_viewpoints.begin(); i != old_viewpoints.end(); ++i ) viewpointsConf.add( *i ); // Loading a viewpoint list from the earth file: if ( !viewpointsConf.empty() ) { std::vector<Viewpoint> viewpoints; const ConfigSet& children = viewpointsConf.children(); if ( children.size() > 0 ) { for( ConfigSet::const_iterator i = children.begin(); i != children.end(); ++i ) { viewpoints.push_back( Viewpoint(*i) ); } } if ( viewpoints.size() > 0 ) { Control* c = ViewpointControlFactory().create(viewpoints, view); if ( c ) mainContainer->addControl( c ); } } // Adding a sky model: if ( useSky || !skyConf.empty() ) { double hours = skyConf.value( "hours", 12.0 ); SkyNode* sky = new SkyNode( mapNode->getMap() ); sky->setDateTime( 2011, 3, 6, hours ); sky->attach( view ); root->addChild( sky ); Control* c = SkyControlFactory().create(sky, view); if ( c ) mainContainer->addControl( c ); } // Adding an ocean model: if ( useOcean || !oceanConf.empty() ) { OceanSurfaceNode* ocean = new OceanSurfaceNode( mapNode, oceanConf ); if ( ocean ) { root->addChild( ocean ); Control* c = OceanControlFactory().create(ocean, view); if ( c ) mainContainer->addControl(c); } } // Loading KML from the command line: if ( !kmlFile.empty() ) { KMLOptions kml_options; kml_options.declutter() = true; kml_options.defaultIconImage() = URI( KML_PUSHPIN_URL ).getImage(); osg::Node* kml = KML::load( URI(kmlFile), mapNode, kml_options ); if ( kml ) { Control* c = AnnotationGraphControlFactory().create(kml, view); if ( c ) { c->setVertAlign( Control::ALIGN_TOP ); canvas->addControl( c ); } root->addChild( kml ); } } // Annotations in the map node externals: if ( !annoConf.empty() ) { osg::Group* annotations = 0L; AnnotationRegistry::instance()->create( mapNode, annoConf, annotations ); if ( annotations ) { root->addChild( annotations ); } } // Configure the de-cluttering engine for labels and annotations: if ( !declutterConf.empty() ) { Decluttering::setOptions( DeclutteringOptions(declutterConf) ); } // Configure the mouse coordinate readout: if ( useCoords ) { LabelControl* readout = new LabelControl(); readout->setBackColor( Color(Color::Black, 0.8) ); readout->setHorizAlign( Control::ALIGN_RIGHT ); readout->setVertAlign( Control::ALIGN_BOTTOM ); Formatter* formatter = useMGRS ? (Formatter*)new MGRSFormatter(MGRSFormatter::PRECISION_1M, 0L, MGRSFormatter::USE_SPACES) : useDMS ? (Formatter*)new LatLongFormatter(LatLongFormatter::FORMAT_DEGREES_MINUTES_SECONDS) : useDD ? (Formatter*)new LatLongFormatter(LatLongFormatter::FORMAT_DECIMAL_DEGREES) : 0L; MouseCoordsTool* mcTool = new MouseCoordsTool( mapNode ); mcTool->addCallback( new MouseCoordsLabelCallback(readout, formatter) ); view->addEventHandler( mcTool ); canvas->addControl( readout ); } root->addChild( canvas ); }
CompositeViewer::CompositeViewer(osg::ArgumentParser& arguments) { constructorInit(); arguments.getApplicationUsage()->addCommandLineOption("--SingleThreaded","Select SingleThreaded threading model for viewer."); arguments.getApplicationUsage()->addCommandLineOption("--CullDrawThreadPerContext","Select CullDrawThreadPerContext threading model for viewer."); arguments.getApplicationUsage()->addCommandLineOption("--DrawThreadPerContext","Select DrawThreadPerContext threading model for viewer."); arguments.getApplicationUsage()->addCommandLineOption("--CullThreadPerCameraDrawThreadPerContext","Select CullThreadPerCameraDrawThreadPerContext threading model for viewer."); arguments.getApplicationUsage()->addCommandLineOption("--run-on-demand","Set the run methods frame rate management to only rendering frames when required."); arguments.getApplicationUsage()->addCommandLineOption("--run-continuous","Set the run methods frame rate management to rendering frames continuously."); arguments.getApplicationUsage()->addCommandLineOption("--run-max-frame-rate","Set the run methods maximum permissible frame rate, 0.0 is default and switching off frame rate capping."); std::string filename; bool readConfig = false; while (arguments.read("-c",filename)) { readConfig = readConfiguration(filename) || readConfig; } while (arguments.read("--SingleThreaded")) setThreadingModel(SingleThreaded); while (arguments.read("--CullDrawThreadPerContext")) setThreadingModel(CullDrawThreadPerContext); while (arguments.read("--DrawThreadPerContext")) setThreadingModel(DrawThreadPerContext); while (arguments.read("--CullThreadPerCameraDrawThreadPerContext")) setThreadingModel(CullThreadPerCameraDrawThreadPerContext); while(arguments.read("--run-on-demand")) { setRunFrameScheme(ON_DEMAND); } while(arguments.read("--run-continuous")) { setRunFrameScheme(CONTINUOUS); } double runMaxFrameRate; while(arguments.read("--run-max-frame-rate", runMaxFrameRate)) { setRunMaxFrameRate(runMaxFrameRate); } osg::DisplaySettings::instance()->readCommandLine(arguments); osgDB::readCommandLine(arguments); }
int seed( osg::ArgumentParser& args ) { //Read the min level unsigned int minLevel = 0; while (args.read("--min-level", minLevel)); //Read the max level unsigned int maxLevel = 5; while (args.read("--max-level", maxLevel)); std::vector< Bounds > bounds; // restrict packaging to user-specified bounds. double xmin=DBL_MAX, ymin=DBL_MAX, xmax=DBL_MIN, ymax=DBL_MIN; while (args.read("--bounds", xmin, ymin, xmax, ymax )) { Bounds b; b.xMin() = xmin, b.yMin() = ymin, b.xMax() = xmax, b.yMax() = ymax; bounds.push_back( b ); } //Read the cache override directory std::string cachePath; while (args.read("--cache-path", cachePath)); //Read the cache type std::string cacheType; while (args.read("--cache-type", cacheType)); bool verbose = args.read("--verbose"); //Read in the earth file. osg::ref_ptr<osg::Node> node = osgDB::readNodeFiles( args ); if ( !node.valid() ) return usage( "Failed to read .earth file." ); MapNode* mapNode = MapNode::findMapNode( node.get() ); if ( !mapNode ) return usage( "Input file was not a .earth file" ); CacheSeed seeder; seeder.setMinLevel( minLevel ); seeder.setMaxLevel( maxLevel ); // Read in an index shapefile std::string index; while (args.read("--index", index)) { //Open the feature source OGRFeatureOptions featureOpt; featureOpt.url() = index; osg::ref_ptr< FeatureSource > features = FeatureSourceFactory::create( featureOpt ); features->initialize(); features->getFeatureProfile(); osg::ref_ptr< FeatureCursor > cursor = features->createFeatureCursor(); while (cursor.valid() && cursor->hasMore()) { osg::ref_ptr< Feature > feature = cursor->nextFeature(); osgEarth::Bounds featureBounds = feature->getGeometry()->getBounds(); GeoExtent ext( feature->getSRS(), featureBounds ); ext = ext.transform( mapNode->getMapSRS() ); bounds.push_back( ext.bounds() ); } } for (unsigned int i = 0; i < bounds.size(); i++) { GeoExtent extent(mapNode->getMapSRS(), bounds[i]); OE_DEBUG << "Adding extent " << extent.toString() << std::endl; seeder.addExtent( extent ); } if (verbose) { seeder.setProgressCallback(new ConsoleProgressCallback); } osg::Timer_t start = osg::Timer::instance()->tick(); seeder.seed( mapNode->getMap() ); osg::Timer_t end = osg::Timer::instance()->tick(); OE_NOTICE << "Completed seeding in " << prettyPrintTime( osg::Timer::instance()->delta_s( start, end ) ) << std::endl; return 0; }
int build(osg::ArgumentParser& arguments) { // the input resource catalog XML file: std::string inCatalogPath; if ( !arguments.read("--build", inCatalogPath) ) return usage("Missing required argument catalog file"); // the output texture atlas image path: std::string inCatalogFile = osgDB::getSimpleFileName(inCatalogPath); std::string outImageFile = osgDB::getNameLessExtension(inCatalogFile) + "_atlas.osgb"; // the output catalog file describing the texture atlas contents: std::string outCatalogFile; outCatalogFile = outImageFile + ".xml"; // check that the input file exists: if ( !osgDB::fileExists(inCatalogPath) ) return usage("Input file not found"); // open the resource library. osg::ref_ptr<osgEarth::Symbology::ResourceLibrary> lib = new osgEarth::Symbology::ResourceLibrary("unnamed", inCatalogPath); if ( !lib->initialize(0L) ) return usage("Error loading input catalog file"); // build the atlas. osgEarth::Util::AtlasBuilder builder; osgEarth::Util::AtlasBuilder::Atlas atlas; // max x/y dimensions: unsigned size; if ( arguments.read("--size", size) ) builder.setSize( size, size ); // auxiliary atlas patterns: std::string pattern; while(arguments.read("--aux", pattern)) builder.addAuxFilePattern(pattern); if ( !builder.build(lib.get(), outImageFile, atlas) ) return usage("Failed to build atlas"); // write the atlas images. osgDB::writeImageFile(*atlas._images.begin()->get(), outImageFile); OE_INFO << LC << "Wrote output image to \"" << outImageFile << "\"" << std::endl; // write any aux images. const std::vector<std::string>& auxPatterns = builder.auxFilePatterns(); for(unsigned i=0; i<auxPatterns.size(); ++i) { std::string auxAtlasFile = osgDB::getNameLessExtension(outImageFile) + "_" + auxPatterns[i] + "." + osgDB::getFileExtension(outImageFile); osgDB::writeImageFile(*atlas._images[i+1].get(), auxAtlasFile); OE_INFO << LC << "Wrote auxiliary image to \"" << auxAtlasFile << "\"" << std::endl; } // write the new catalog: osgEarth::XmlDocument catXML( atlas._lib->getConfig() ); std::ofstream catOut(outCatalogFile.c_str()); if ( !catOut.is_open() ) return usage("Failed to open output catalog file for writing"); catXML.store(catOut); catOut.close(); OE_INFO << LC << "Wrote output catalog to \"" << outCatalogFile<< "\"" << std::endl; }
/** Packages an image layer as a TMS folder. */ int makeTMS( osg::ArgumentParser& args ) { // see if the user wants to override the type extension (imagery only) std::string extension; args.read( "--ext", extension ); // verbosity? bool verbose = !args.read( "--quiet" ); // find a .earth file on the command line std::string earthFile = findArgumentWithExtension(args, ".earth"); /* if ( earthFile.empty() ) return usage( "Missing required .earth file" ); */ // folder to which to write the TMS archive. std::string rootFolder; if ( !args.read( "--out", rootFolder ) ) rootFolder = Stringify() << earthFile << ".tms_repo"; // whether to overwrite existing tile files bool overwrite = false; if ( args.read("--overwrite") ) overwrite = true; // write out an earth file std::string outEarth; args.read("--out-earth", outEarth); std::string dbOptions; args.read("--db-options", dbOptions); std::string::size_type n = 0; while ((n=dbOptions.find('"', n))!=dbOptions.npos) { dbOptions.erase(n,1); } osg::ref_ptr<osgDB::Options> options = new osgDB::Options(dbOptions); std::vector< Bounds > bounds; // restrict packaging to user-specified bounds. double xmin=DBL_MAX, ymin=DBL_MAX, xmax=DBL_MIN, ymax=DBL_MIN; while (args.read("--bounds", xmin, ymin, xmax, ymax )) { Bounds b; b.xMin() = xmin, b.yMin() = ymin, b.xMax() = xmax, b.yMax() = ymax; bounds.push_back( b ); } // max level to which to generate unsigned maxLevel = ~0; args.read( "--max-level", maxLevel ); // whether to keep 'empty' tiles bool keepEmpties = args.read("--keep-empties"); bool continueSingleColor = args.read("--continue-single-color"); // load up the map osg::ref_ptr<MapNode> mapNode = MapNode::load( args ); if ( !mapNode.valid() ) return usage( "Failed to load a valid .earth file" ); // create a folder for the output osgDB::makeDirectory(rootFolder); if ( !osgDB::fileExists(rootFolder) ) return usage("Failed to create root output folder" ); Map* map = mapNode->getMap(); // fire up a packager: TMSPackager packager( map->getProfile(), options); packager.setVerbose( verbose ); packager.setOverwrite( overwrite ); packager.setKeepEmptyImageTiles( keepEmpties ); packager.setSubdivideSingleColorImageTiles( continueSingleColor ); if ( maxLevel != ~0 ) packager.setMaxLevel( maxLevel ); if (bounds.size() > 0) { for (unsigned int i = 0; i < bounds.size(); ++i) { Bounds b = bounds[i]; if ( b.isValid() ) packager.addExtent( GeoExtent(map->getProfile()->getSRS(), b) ); } } // new map for an output earth file if necessary. osg::ref_ptr<Map> outMap = 0L; if ( !outEarth.empty() ) { // copy the options from the source map first outMap = new Map(map->getInitialMapOptions()); } // establish the output path of the earth file, if applicable: std::string outEarthFile = osgDB::concatPaths(rootFolder, osgDB::getSimpleFileName(outEarth)); // package any image layers that are enabled: ImageLayerVector imageLayers; map->getImageLayers( imageLayers ); unsigned counter = 0; for( ImageLayerVector::iterator i = imageLayers.begin(); i != imageLayers.end(); ++i, ++counter ) { ImageLayer* layer = i->get(); if ( layer->getImageLayerOptions().enabled() == true ) { std::string layerFolder = toLegalFileName( layer->getName() ); if ( layerFolder.empty() ) layerFolder = Stringify() << "image_layer_" << counter; if ( verbose ) { OE_NOTICE << LC << "Packaging image layer \"" << layerFolder << "\"" << std::endl; } osg::ref_ptr< ConsoleProgressCallback > progress = new ConsoleProgressCallback(); std::string layerRoot = osgDB::concatPaths( rootFolder, layerFolder ); TMSPackager::Result r = packager.package( layer, layerRoot, progress, extension ); if ( r.ok ) { // save to the output map if requested: if ( outMap.valid() ) { // new TMS driver info: TMSOptions tms; tms.url() = URI( osgDB::concatPaths(layerFolder, "tms.xml"), outEarthFile ); ImageLayerOptions layerOptions( layer->getName(), tms ); layerOptions.mergeConfig( layer->getInitialOptions().getConfig(true) ); layerOptions.cachePolicy() = CachePolicy::NO_CACHE; outMap->addImageLayer( new ImageLayer(layerOptions) ); } } else { OE_WARN << LC << r.message << std::endl; } } else if ( verbose ) { OE_NOTICE << LC << "Skipping disabled layer \"" << layer->getName() << "\"" << std::endl; } } // package any elevation layers that are enabled: counter = 0; ElevationLayerVector elevationLayers; map->getElevationLayers( elevationLayers ); for( ElevationLayerVector::iterator i = elevationLayers.begin(); i != elevationLayers.end(); ++i, ++counter ) { ElevationLayer* layer = i->get(); if ( layer->getElevationLayerOptions().enabled() == true ) { std::string layerFolder = toLegalFileName( layer->getName() ); if ( layerFolder.empty() ) layerFolder = Stringify() << "elevation_layer_" << counter; if ( verbose ) { OE_NOTICE << LC << "Packaging elevation layer \"" << layerFolder << "\"" << std::endl; } std::string layerRoot = osgDB::concatPaths( rootFolder, layerFolder ); TMSPackager::Result r = packager.package( layer, layerRoot ); if ( r.ok ) { // save to the output map if requested: if ( outMap.valid() ) { // new TMS driver info: TMSOptions tms; tms.url() = URI( osgDB::concatPaths(layerFolder, "tms.xml"), outEarthFile ); ElevationLayerOptions layerOptions( layer->getName(), tms ); layerOptions.mergeConfig( layer->getInitialOptions().getConfig(true) ); layerOptions.cachePolicy() = CachePolicy::NO_CACHE; outMap->addElevationLayer( new ElevationLayer(layerOptions) ); } } else { OE_WARN << LC << r.message << std::endl; } } else if ( verbose ) { OE_NOTICE << LC << "Skipping disabled layer \"" << layer->getName() << "\"" << std::endl; } } // Finally, write an earth file if requested: if ( outMap.valid() ) { MapNodeOptions outNodeOptions = mapNode->getMapNodeOptions(); osg::ref_ptr<MapNode> outMapNode = new MapNode(outMap.get(), outNodeOptions); if ( !osgDB::writeNodeFile(*outMapNode.get(), outEarthFile) ) { OE_WARN << LC << "Error writing earth file to \"" << outEarthFile << "\"" << std::endl; } else if ( verbose ) { OE_NOTICE << LC << "Wrote earth file to \"" << outEarthFile << "\"" << std::endl; } } return 0; }
Viewer::Viewer(osg::ArgumentParser& arguments) { _viewerBase = this; constructorInit(); // Add help for command-line options read here arguments.getApplicationUsage()->addCommandLineOption("--SingleThreaded","Select SingleThreaded threading model for viewer."); arguments.getApplicationUsage()->addCommandLineOption("--CullDrawThreadPerContext","Select CullDrawThreadPerContext threading model for viewer."); arguments.getApplicationUsage()->addCommandLineOption("--DrawThreadPerContext","Select DrawThreadPerContext threading model for viewer."); arguments.getApplicationUsage()->addCommandLineOption("--CullThreadPerCameraDrawThreadPerContext","Select CullThreadPerCameraDrawThreadPerContext threading model for viewer."); arguments.getApplicationUsage()->addCommandLineOption("--clear-color <color>","Set the background color of the viewer in the form \"r,g,b[,a]\"."); arguments.getApplicationUsage()->addCommandLineOption("--screen <num>","Set the screen to use when multiple screens are present."); arguments.getApplicationUsage()->addCommandLineOption("--window <x y w h>","Set the position (x,y) and size (w,h) of the viewer window."); // FIXME: Uncomment these lines when the options have been documented properly //arguments.getApplicationUsage()->addCommandLineOption("--3d-sd",""); //arguments.getApplicationUsage()->addCommandLineOption("--panoramic-sd",""); //arguments.getApplicationUsage()->addCommandLineOption("--radius",""); //arguments.getApplicationUsage()->addCommandLineOption("--collar",""); //arguments.getApplicationUsage()->addCommandLineOption("--im",""); std::string filename; bool readConfig = false; while (arguments.read("-c",filename)) { readConfig = readConfiguration(filename) || readConfig; } while (arguments.read("--SingleThreaded")) setThreadingModel(SingleThreaded); while (arguments.read("--CullDrawThreadPerContext")) setThreadingModel(CullDrawThreadPerContext); while (arguments.read("--DrawThreadPerContext")) setThreadingModel(DrawThreadPerContext); while (arguments.read("--CullThreadPerCameraDrawThreadPerContext")) setThreadingModel(CullThreadPerCameraDrawThreadPerContext); osg::DisplaySettings::instance()->readCommandLine(arguments); osgDB::readCommandLine(arguments); std::string colorStr; while (arguments.read("--clear-color",colorStr)) { float r, g, b; float a = 1.0f; int cnt = sscanf( colorStr.c_str(), "%f,%f,%f,%f", &r, &g, &b, &a ); if( cnt==3 || cnt==4 ) getCamera()->setClearColor( osg::Vec4(r,g,b,a) ); else osg::notify(osg::WARN)<<"Invalid clear color \""<<colorStr<<"\""<<std::endl; } int screenNum = -1; while (arguments.read("--screen",screenNum)) {} int x = -1, y = -1, width = -1, height = -1; while (arguments.read("--window",x,y,width,height)) {} bool ss3d = false; bool wowvx20 = false; bool wowvx42 = false; if ((wowvx20=arguments.read("--wowvx-20")) || (wowvx42=arguments.read("--wowvx-42")) || arguments.read("--wowvx")) { int wow_content=0x02, wow_factor=0x40, wow_offset=0x80; float wow_Zd, wow_vz, wow_M, wow_C; if (wowvx20){ wow_Zd = 0.459813f; wow_vz = 6.180772f; wow_M = -1586.34f; wow_C = 127.5f; } else if (wowvx42){ wow_Zd = 0.467481f; wow_vz = 7.655192f; wow_M = -1960.37f; wow_C = 127.5f; } while (arguments.read("--wow-content",wow_content)) {} while (arguments.read("--wow-factor",wow_factor)) {} while (arguments.read("--wow-offset",wow_offset)) {} while (arguments.read("--wow-zd",wow_Zd)) {} while (arguments.read("--wow-vz",wow_vz)) {} while (arguments.read("--wow-M",wow_M)) {} while (arguments.read("--wow-C",wow_C)) {} if (screenNum<0) screenNum = 0; setUpViewForWoWVxDisplay( screenNum, wow_content, wow_factor, wow_offset, wow_Zd, wow_vz, wow_M, wow_C ); } else if ((ss3d=arguments.read("--3d-sd")) || arguments.read("--panoramic-sd")) { double radius = 1.0; while (arguments.read("--radius",radius)) {} double collar = 0.45; while (arguments.read("--collar",collar)) {} std::string intensityMapFilename; while (arguments.read("--im",intensityMapFilename)) {} osg::ref_ptr<osg::Image> intensityMap = intensityMapFilename.empty() ? 0 : osgDB::readImageFile(intensityMapFilename); if (screenNum<0) screenNum = 0; if (ss3d) { setThreadingModel(SingleThreaded); setUpViewFor3DSphericalDisplay(radius, collar, screenNum, intensityMap.get()); } else { setThreadingModel(SingleThreaded); setUpViewForPanoramicSphericalDisplay(radius, collar, screenNum, intensityMap.get()); } } else if (width>0 && height>0) { if (screenNum>=0) setUpViewInWindow(x, y, width, height, screenNum); else setUpViewInWindow(x,y,width,height); } else if (screenNum>=0) { setUpViewOnSingleScreen(screenNum); } }
/** Packages an image layer as a TMS folder. */ int makeTMS( osg::ArgumentParser& args ) { // see if the user wants to override the type extension (imagery only) std::string extension = "png"; args.read( "--ext", extension ); // verbosity? bool verbose = !args.read( "--quiet" ); // find a .earth file on the command line std::string earthFile = findArgumentWithExtension(args, ".earth"); if ( earthFile.empty() ) return usage( "Missing required .earth file" ); // folder to which to write the TMS archive. std::string rootFolder; if ( !args.read( "--out", rootFolder ) ) rootFolder = Stringify() << earthFile << ".tms_repo"; // max level to which to generate unsigned maxLevel = ~0; args.read( "--max-level", maxLevel ); // load up the map osg::ref_ptr<MapNode> mapNode = MapNode::load( args ); if ( !mapNode.valid() ) return usage( "Failed to load a valid .earth file" ); // create a folder for the output osgDB::makeDirectory(rootFolder); if ( !osgDB::fileExists(rootFolder) ) return usage("Failed to create root output folder" ); Map* map = mapNode->getMap(); // fire up a packager: TMSPackager packager( map->getProfile() ); packager.setVerbose( verbose ); if ( maxLevel != ~0 ) packager.setMaxLevel( maxLevel ); // package any image layers that are enabled: ImageLayerVector imageLayers; map->getImageLayers( imageLayers ); unsigned counter = 0; for( ImageLayerVector::iterator i = imageLayers.begin(); i != imageLayers.end(); ++i, ++counter ) { ImageLayer* layer = i->get(); if ( layer->getImageLayerOptions().enabled() == true ) { std::string layerFolder = toLegalFileName( layer->getName() ); if ( layerFolder.empty() ) layerFolder = Stringify() << "image_layer_" << counter; if ( verbose ) { OE_NOTICE << LC << "Packaging image layer \"" << layerFolder << "\"" << std::endl; } std::string layerRoot = osgDB::concatPaths( rootFolder, layerFolder ); TMSPackager::Result r = packager.package( layer, layerRoot, extension ); if ( !r.ok ) { OE_WARN << LC << r.message << std::endl; } } else if ( verbose ) { OE_NOTICE << LC << "Skipping disabled layer \"" << layer->getName() << "\"" << std::endl; } } // package any elevation layers that are enabled: counter = 0; ElevationLayerVector elevationLayers; map->getElevationLayers( elevationLayers ); for( ElevationLayerVector::iterator i = elevationLayers.begin(); i != elevationLayers.end(); ++i, ++counter ) { ElevationLayer* layer = i->get(); if ( layer->getElevationLayerOptions().enabled() == true ) { std::string layerFolder = toLegalFileName( layer->getName() ); if ( layerFolder.empty() ) layerFolder = Stringify() << "elevation_layer_" << counter; if ( verbose ) { OE_NOTICE << LC << "Packaging elevation layer \"" << layerFolder << "\"" << std::endl; } std::string layerRoot = osgDB::concatPaths( rootFolder, layerFolder ); packager.package( layer, layerRoot ); } else if ( verbose ) { OE_NOTICE << LC << "Skipping disabled layer \"" << layer->getName() << "\"" << std::endl; } } return 0; }
void MapNodeHelper::parse(MapNode* mapNode, osg::ArgumentParser& args, osgViewer::View* view, osg::Group* root, Container* userContainer ) const { if ( !root ) root = mapNode; // options to use for the load osg::ref_ptr<osgDB::Options> dbOptions = Registry::instance()->cloneOrCreateOptions(); // parse out custom example arguments first: bool useMGRS = args.read("--mgrs"); bool useDMS = args.read("--dms"); bool useDD = args.read("--dd"); bool useCoords = args.read("--coords") || useMGRS || useDMS || useDD; bool useAutoClip = args.read("--autoclip"); bool showActivity = args.read("--activity"); bool useLogDepth = args.read("--logdepth"); bool useLogDepth2 = args.read("--logdepth2"); bool kmlUI = args.read("--kmlui"); std::string kmlFile; args.read( "--kml", kmlFile ); std::string imageFolder; args.read( "--images", imageFolder ); std::string imageExtensions; args.read("--image-extensions", imageExtensions); // animation path: std::string animpath; if ( args.read("--path", animpath) ) { view->setCameraManipulator( new osgGA::AnimationPathManipulator(animpath) ); } // Install a new Canvas for our UI controls, or use one that already exists. ControlCanvas* canvas = ControlCanvas::getOrCreate( view ); Container* mainContainer; if ( userContainer ) { mainContainer = userContainer; } else { mainContainer = new VBox(); mainContainer->setAbsorbEvents( true ); mainContainer->setBackColor( Color(Color::Black, 0.8) ); mainContainer->setHorizAlign( Control::ALIGN_LEFT ); mainContainer->setVertAlign( Control::ALIGN_BOTTOM ); } canvas->addControl( mainContainer ); // Add an event handler to toggle the canvas with a key press; view->addEventHandler(new ToggleCanvasEventHandler(canvas, 'y')); // look for external data in the map node: const Config& externals = mapNode->externalConfig(); // some terrain effects. // TODO: Most of these are likely to move into extensions. const Config& vertScaleConf = externals.child("vertical_scale"); // Loading KML from the command line: if ( !kmlFile.empty() ) { KMLOptions kml_options; kml_options.declutter() = true; // set up a default icon for point placemarks: IconSymbol* defaultIcon = new IconSymbol(); defaultIcon->url()->setLiteral(KML_PUSHPIN_URL); kml_options.defaultIconSymbol() = defaultIcon; TextSymbol* defaultText = new TextSymbol(); defaultText->halo() = Stroke(0.3,0.3,0.3,1.0); kml_options.defaultTextSymbol() = defaultText; osg::Node* kml = KML::load( URI(kmlFile), mapNode, kml_options ); if ( kml ) { if (kmlUI) { Control* c = AnnotationGraphControlFactory().create(kml, view); if ( c ) { c->setVertAlign( Control::ALIGN_TOP ); canvas->addControl( c ); } } root->addChild( kml ); } else { OE_NOTICE << "Failed to load " << kmlFile << std::endl; } } //// Configure the de-cluttering engine for labels and annotations: //if ( !screenSpaceLayoutConf.empty() ) //{ // ScreenSpaceLayout::setOptions( ScreenSpaceLayoutOptions(screenSpaceLayoutConf) ); //} // Configure the mouse coordinate readout: if ( useCoords ) { LabelControl* readout = new LabelControl(); readout->setBackColor( Color(Color::Black, 0.8) ); readout->setHorizAlign( Control::ALIGN_RIGHT ); readout->setVertAlign( Control::ALIGN_BOTTOM ); Formatter* formatter = useMGRS ? (Formatter*)new MGRSFormatter(MGRSFormatter::PRECISION_1M, 0L, MGRSFormatter::USE_SPACES) : useDMS ? (Formatter*)new LatLongFormatter(LatLongFormatter::FORMAT_DEGREES_MINUTES_SECONDS) : useDD ? (Formatter*)new LatLongFormatter(LatLongFormatter::FORMAT_DECIMAL_DEGREES) : 0L; MouseCoordsTool* mcTool = new MouseCoordsTool( mapNode ); mcTool->addCallback( new MouseCoordsLabelCallback(readout, formatter) ); view->addEventHandler( mcTool ); canvas->addControl( readout ); } // Configure for an ortho camera: if ( args.read("--ortho") ) { view->getCamera()->setProjectionMatrixAsOrtho(-1, 1, -1, 1, 0, 1); } // activity monitor (debugging) if ( showActivity ) { VBox* vbox = new VBox(); vbox->setBackColor( Color(Color::Black, 0.8) ); vbox->setHorizAlign( Control::ALIGN_RIGHT ); vbox->setVertAlign( Control::ALIGN_BOTTOM ); view->addEventHandler( new ActivityMonitorTool(vbox) ); canvas->addControl( vbox ); } // Install an auto clip plane clamper if ( useAutoClip ) { mapNode->addCullCallback( new AutoClipPlaneCullCallback(mapNode) ); } // Install logarithmic depth buffer on main camera if ( useLogDepth ) { OE_INFO << LC << "Activating logarithmic depth buffer (vertex-only) on main camera" << std::endl; osgEarth::Util::LogarithmicDepthBuffer logDepth; logDepth.setUseFragDepth( false ); logDepth.install( view->getCamera() ); } else if ( useLogDepth2 ) { OE_INFO << LC << "Activating logarithmic depth buffer (precise) on main camera" << std::endl; osgEarth::Util::LogarithmicDepthBuffer logDepth; logDepth.setUseFragDepth( true ); logDepth.install( view->getCamera() ); } // Scan for images if necessary. if ( !imageFolder.empty() ) { std::vector<std::string> extensions; if ( !imageExtensions.empty() ) StringTokenizer( imageExtensions, extensions, ",;", "", false, true ); if ( extensions.empty() ) extensions.push_back( "tif" ); OE_INFO << LC << "Loading images from " << imageFolder << "..." << std::endl; ImageLayerVector imageLayers; DataScanner scanner; scanner.findImageLayers( imageFolder, extensions, imageLayers ); if ( imageLayers.size() > 0 ) { mapNode->getMap()->beginUpdate(); for( ImageLayerVector::iterator i = imageLayers.begin(); i != imageLayers.end(); ++i ) { mapNode->getMap()->addImageLayer( i->get() ); } mapNode->getMap()->endUpdate(); } OE_INFO << LC << "...found " << imageLayers.size() << " image layers." << std::endl; } // Install vertical scaler. // TODO: deprecate this, or move it to an extension. if ( !vertScaleConf.empty() ) { mapNode->getTerrainEngine()->addEffect( new VerticalScale(vertScaleConf) ); } // Generic named value uniform with min/max. VBox* uniformBox = 0L; while( args.find( "--uniform" ) >= 0 ) { std::string name; float minval, maxval; if ( args.read( "--uniform", name, minval, maxval ) ) { if ( uniformBox == 0L ) { uniformBox = new VBox(); uniformBox->setBackColor(0,0,0,0.5); uniformBox->setAbsorbEvents( true ); canvas->addControl( uniformBox ); } osg::Uniform* uniform = new osg::Uniform(osg::Uniform::FLOAT, name); uniform->set( minval ); root->getOrCreateStateSet()->addUniform( uniform, osg::StateAttribute::OVERRIDE ); HBox* box = new HBox(); box->addControl( new LabelControl(name) ); HSliderControl* hs = box->addControl( new HSliderControl(minval, maxval, minval, new ApplyValueUniform(uniform))); hs->setHorizFill(true, 200); box->addControl( new LabelControl(hs) ); uniformBox->addControl( box ); OE_INFO << LC << "Installed uniform controller for " << name << std::endl; } } // Map inspector: if (args.read("--inspect")) { mapNode->addExtension( Extension::create("mapinspector", ConfigOptions()) ); } // Memory monitor: if (args.read("--monitor")) { mapNode->addExtension(Extension::create("monitor", ConfigOptions()) ); } // Simple sky model: if (args.read("--sky")) { mapNode->addExtension(Extension::create("sky_simple", ConfigOptions()) ); } // Simple ocean model: if (args.read("--ocean")) { mapNode->addExtension(Extension::create("ocean_simple", ConfigOptions())); } // Arbitrary extension: std::string extname; if (args.read("--extension", extname)) { Extension* ext = Extension::create(extname, ConfigOptions()); if (ext) mapNode->addExtension(ext); } // Hook up the extensions! for(std::vector<osg::ref_ptr<Extension> >::const_iterator eiter = mapNode->getExtensions().begin(); eiter != mapNode->getExtensions().end(); ++eiter) { Extension* e = eiter->get(); // Check for a View interface: ExtensionInterface<osg::View>* viewIF = ExtensionInterface<osg::View>::get( e ); if ( viewIF ) viewIF->connect( view ); // Check for a Control interface: ExtensionInterface<Control>* controlIF = ExtensionInterface<Control>::get( e ); if ( controlIF ) controlIF->connect( mainContainer ); } // Shadowing. This is last because it needs access to a light which may be provided // by one of the Sky extensions. if (args.read("--shadows")) { int unit; if ( mapNode->getTerrainEngine()->getResources()->reserveTextureImageUnit(unit, "ShadowCaster") ) { ShadowCaster* caster = new ShadowCaster(); caster->setTextureImageUnit( unit ); caster->setLight( view->getLight() ); caster->getShadowCastingGroup()->addChild( mapNode->getModelLayerGroup() ); //insertParent(caster, mapNode); //root = findTopOfGraph(caster)->asGroup(); if ( mapNode->getNumParents() > 0 ) { insertGroup(caster, mapNode->getParent(0)); } else { caster->addChild(mapNode); root = caster; } } } root->addChild( canvas ); }
void MapNodeHelper::parse(MapNode* mapNode, osg::ArgumentParser& args, osgViewer::View* view, osg::Group* root, Control* userControl ) const { // this is a dubious move. if ( !root ) root = mapNode; // options to use for the load osg::ref_ptr<osgDB::Options> dbOptions = Registry::instance()->cloneOrCreateOptions(); // parse out custom example arguments first: bool useSky = args.read("--sky"); bool useOcean = args.read("--ocean"); bool useMGRS = args.read("--mgrs"); bool useDMS = args.read("--dms"); bool useDD = args.read("--dd"); bool useCoords = args.read("--coords") || useMGRS || useDMS || useDD; bool useOrtho = args.read("--ortho"); bool useAutoClip = args.read("--autoclip"); float ambientBrightness = 0.4f; args.read("--ambientBrightness", ambientBrightness); std::string kmlFile; args.read( "--kml", kmlFile ); // install a canvas for any UI controls we plan to create: ControlCanvas* canvas = ControlCanvas::get(view, false); Container* mainContainer = canvas->addControl( new VBox() ); mainContainer->setBackColor( Color(Color::Black, 0.8) ); mainContainer->setHorizAlign( Control::ALIGN_LEFT ); mainContainer->setVertAlign( Control::ALIGN_BOTTOM ); // install the user control: if ( userControl ) mainContainer->addControl( userControl ); // look for external data in the map node: const Config& externals = mapNode->externalConfig(); const Config& skyConf = externals.child("sky"); const Config& oceanConf = externals.child("ocean"); const Config& annoConf = externals.child("annotations"); const Config& declutterConf = externals.child("decluttering"); Config viewpointsConf = externals.child("viewpoints"); // backwards-compatibility: read viewpoints at the top level: const ConfigSet& old_viewpoints = externals.children("viewpoint"); for( ConfigSet::const_iterator i = old_viewpoints.begin(); i != old_viewpoints.end(); ++i ) viewpointsConf.add( *i ); // Loading a viewpoint list from the earth file: if ( !viewpointsConf.empty() ) { std::vector<Viewpoint> viewpoints; const ConfigSet& children = viewpointsConf.children(); if ( children.size() > 0 ) { for( ConfigSet::const_iterator i = children.begin(); i != children.end(); ++i ) { viewpoints.push_back( Viewpoint(*i) ); } } if ( viewpoints.size() > 0 ) { Control* c = ViewpointControlFactory().create(viewpoints, view); if ( c ) mainContainer->addControl( c ); } } // Adding a sky model: if ( useSky || !skyConf.empty() ) { double hours = skyConf.value( "hours", 12.0 ); SkyNode* sky = new SkyNode( mapNode->getMap() ); sky->setAmbientBrightness( ambientBrightness ); sky->setDateTime( 2011, 3, 6, hours ); sky->attach( view ); root->addChild( sky ); Control* c = SkyControlFactory().create(sky, view); if ( c ) mainContainer->addControl( c ); } // Adding an ocean model: if ( useOcean || !oceanConf.empty() ) { OceanSurfaceNode* ocean = new OceanSurfaceNode( mapNode, oceanConf ); if ( ocean ) { root->addChild( ocean ); Control* c = OceanControlFactory().create(ocean, view); if ( c ) mainContainer->addControl(c); } } // Loading KML from the command line: if ( !kmlFile.empty() ) { KMLOptions kml_options; kml_options.declutter() = true; // set up a default icon for point placemarks: IconSymbol* defaultIcon = new IconSymbol(); defaultIcon->url()->setLiteral(KML_PUSHPIN_URL); kml_options.defaultIconSymbol() = defaultIcon; osg::Node* kml = KML::load( URI(kmlFile), mapNode, kml_options ); if ( kml ) { Control* c = AnnotationGraphControlFactory().create(kml, view); if ( c ) { c->setVertAlign( Control::ALIGN_TOP ); canvas->addControl( c ); } root->addChild( kml ); } } // Annotations in the map node externals: if ( !annoConf.empty() ) { osg::Group* annotations = 0L; AnnotationRegistry::instance()->create( mapNode, annoConf, dbOptions.get(), annotations ); if ( annotations ) { root->addChild( annotations ); } } // Configure the de-cluttering engine for labels and annotations: if ( !declutterConf.empty() ) { Decluttering::setOptions( DeclutteringOptions(declutterConf) ); } // Configure the mouse coordinate readout: if ( useCoords ) { LabelControl* readout = new LabelControl(); readout->setBackColor( Color(Color::Black, 0.8) ); readout->setHorizAlign( Control::ALIGN_RIGHT ); readout->setVertAlign( Control::ALIGN_BOTTOM ); Formatter* formatter = useMGRS ? (Formatter*)new MGRSFormatter(MGRSFormatter::PRECISION_1M, 0L, MGRSFormatter::USE_SPACES) : useDMS ? (Formatter*)new LatLongFormatter(LatLongFormatter::FORMAT_DEGREES_MINUTES_SECONDS) : useDD ? (Formatter*)new LatLongFormatter(LatLongFormatter::FORMAT_DECIMAL_DEGREES) : 0L; MouseCoordsTool* mcTool = new MouseCoordsTool( mapNode ); mcTool->addCallback( new MouseCoordsLabelCallback(readout, formatter) ); view->addEventHandler( mcTool ); canvas->addControl( readout ); } // Configure for an ortho camera: if ( useOrtho ) { EarthManipulator* manip = dynamic_cast<EarthManipulator*>(view->getCameraManipulator()); if ( manip ) { manip->getSettings()->setCameraProjection( EarthManipulator::PROJ_ORTHOGRAPHIC ); } } // Install an auto clip plane clamper if ( useAutoClip ) { #if 0 HorizonClipNode* hcn = new HorizonClipNode( mapNode ); if ( mapNode->getNumParents() == 1 ) { osg::Group* parent = mapNode->getParent(0); hcn->addChild( mapNode ); parent->replaceChild( mapNode, hcn ); } #else mapNode->addCullCallback( new AutoClipPlaneCullCallback(mapNode) ); #endif } root->addChild( canvas ); }
Viewer::Viewer(osg::ArgumentParser& arguments) { _viewerBase = this; constructorInit(); // Add help for command-line options read here arguments.getApplicationUsage()->addCommandLineOption("--SingleThreaded","Select SingleThreaded threading model for viewer."); arguments.getApplicationUsage()->addCommandLineOption("--CullDrawThreadPerContext","Select CullDrawThreadPerContext threading model for viewer."); arguments.getApplicationUsage()->addCommandLineOption("--DrawThreadPerContext","Select DrawThreadPerContext threading model for viewer."); arguments.getApplicationUsage()->addCommandLineOption("--CullThreadPerCameraDrawThreadPerContext","Select CullThreadPerCameraDrawThreadPerContext threading model for viewer."); arguments.getApplicationUsage()->addCommandLineOption("--clear-color <color>","Set the background color of the viewer in the form \"r,g,b[,a]\"."); arguments.getApplicationUsage()->addCommandLineOption("--screen <num>","Set the screen to use when multiple screens are present."); arguments.getApplicationUsage()->addCommandLineOption("--window <x y w h>","Set the position (x,y) and size (w,h) of the viewer window."); arguments.getApplicationUsage()->addCommandLineOption("--run-on-demand","Set the run methods frame rate management to only rendering frames when required."); arguments.getApplicationUsage()->addCommandLineOption("--run-continuous","Set the run methods frame rate management to rendering frames continuously."); arguments.getApplicationUsage()->addCommandLineOption("--run-max-frame-rate","Set the run methods maximum permissable frame rate, 0.0 is default and switching off frame rate capping."); arguments.getApplicationUsage()->addCommandLineOption("--enable-object-cache","Enable caching of objects, images, etc."); // FIXME: Uncomment these lines when the options have been documented properly //arguments.getApplicationUsage()->addCommandLineOption("--3d-sd",""); //arguments.getApplicationUsage()->addCommandLineOption("--panoramic-sd",""); //arguments.getApplicationUsage()->addCommandLineOption("--radius",""); //arguments.getApplicationUsage()->addCommandLineOption("--collar",""); //arguments.getApplicationUsage()->addCommandLineOption("--im",""); if (arguments.read("--ico")) { setIncrementalCompileOperation(new osgUtil::IncrementalCompileOperation()); } std::string filename; bool readConfig = false; while (arguments.read("-c",filename)) { readConfig = readConfiguration(filename) || readConfig; } // Enable caching? while (arguments.read("--enable-object-cache")) { if (osgDB::Registry::instance()->getOptions()==0) osgDB::Registry::instance()->setOptions(new osgDB::Options()); osgDB::Registry::instance()->getOptions()->setObjectCacheHint(osgDB::Options::CACHE_ALL); } while (arguments.read("--SingleThreaded")) setThreadingModel(SingleThreaded); while (arguments.read("--CullDrawThreadPerContext")) setThreadingModel(CullDrawThreadPerContext); while (arguments.read("--DrawThreadPerContext")) setThreadingModel(DrawThreadPerContext); while (arguments.read("--CullThreadPerCameraDrawThreadPerContext")) setThreadingModel(CullThreadPerCameraDrawThreadPerContext); osg::DisplaySettings::instance()->readCommandLine(arguments); osgDB::readCommandLine(arguments); std::string colorStr; while (arguments.read("--clear-color",colorStr)) { float r, g, b; float a = 1.0f; int cnt = sscanf( colorStr.c_str(), "%f,%f,%f,%f", &r, &g, &b, &a ); if( cnt==3 || cnt==4 ) { getCamera()->setClearColor( osg::Vec4(r,g,b,a) ); } else { OSG_WARN<<"Invalid clear color \""<<colorStr<<"\""<<std::endl; } } while(arguments.read("--run-on-demand")) { setRunFrameScheme(ON_DEMAND); } while(arguments.read("--run-continuous")) { setRunFrameScheme(CONTINUOUS); } double runMaxFrameRate; while(arguments.read("--run-max-frame-rate", runMaxFrameRate)) { setRunMaxFrameRate(runMaxFrameRate); } int screenNum = -1; while (arguments.read("--screen",screenNum)) {} int x = -1, y = -1, width = -1, height = -1; while (arguments.read("--window",x,y,width,height)) {} bool ss3d = false; bool wowvx20 = false; bool wowvx42 = false; if ((wowvx20=arguments.read("--wowvx-20")) || (wowvx42=arguments.read("--wowvx-42")) || arguments.read("--wowvx")) { int wow_content=0x02, wow_factor=0x40, wow_offset=0x80; float wow_Zd, wow_vz, wow_M, wow_C; if (wowvx20){ wow_Zd = 0.459813f; wow_vz = 6.180772f; wow_M = -1586.34f; wow_C = 127.5f; } else if (wowvx42){ wow_Zd = 0.467481f; wow_vz = 7.655192f; wow_M = -1960.37f; wow_C = 127.5f; } while (arguments.read("--wow-content",wow_content)) {} while (arguments.read("--wow-factor",wow_factor)) {} while (arguments.read("--wow-offset",wow_offset)) {} while (arguments.read("--wow-zd",wow_Zd)) {} while (arguments.read("--wow-vz",wow_vz)) {} while (arguments.read("--wow-M",wow_M)) {} while (arguments.read("--wow-C",wow_C)) {} if (screenNum<0) screenNum = 0; setUpViewForWoWVxDisplay( screenNum, wow_content, wow_factor, wow_offset, wow_Zd, wow_vz, wow_M, wow_C ); } else if ((ss3d=arguments.read("--3d-sd")) || arguments.read("--panoramic-sd")) { double radius = 1.0; while (arguments.read("--radius",radius)) {} double collar = 0.45; while (arguments.read("--collar",collar)) {} std::string intensityMapFilename; while (arguments.read("--im",intensityMapFilename)) {} osg::ref_ptr<osg::Image> intensityMap = intensityMapFilename.empty() ? 0 : osgDB::readImageFile(intensityMapFilename); if (screenNum<0) screenNum = 0; if (ss3d) { setThreadingModel(SingleThreaded); setUpViewFor3DSphericalDisplay(radius, collar, screenNum, intensityMap.get()); } else { setThreadingModel(SingleThreaded); setUpViewForPanoramicSphericalDisplay(radius, collar, screenNum, intensityMap.get()); } } else if (width>0 && height>0) { if (screenNum>=0) setUpViewInWindow(x, y, width, height, screenNum); else setUpViewInWindow(x,y,width,height); } else if (screenNum>=0) { setUpViewOnSingleScreen(screenNum); } }
void MapNodeHelper::parse(MapNode* mapNode, osg::ArgumentParser& args, osgViewer::View* view, osg::Group* root, Container* userContainer ) const { if ( !root ) root = mapNode; // options to use for the load osg::ref_ptr<osgDB::Options> dbOptions = Registry::instance()->cloneOrCreateOptions(); // parse out custom example arguments first: bool useSky = args.read("--sky"); bool useOcean = args.read("--ocean"); bool useMGRS = args.read("--mgrs"); bool useDMS = args.read("--dms"); bool useDD = args.read("--dd"); bool useCoords = args.read("--coords") || useMGRS || useDMS || useDD; bool useOrtho = args.read("--ortho"); bool useAutoClip = args.read("--autoclip"); bool useShadows = args.read("--shadows"); bool animateSky = args.read("--animate-sky"); bool showActivity = args.read("--activity"); bool useLogDepth = args.read("--logdepth"); bool useLogDepth2 = args.read("--logdepth2"); bool kmlUI = args.read("--kmlui"); bool inspect = args.read("--inspect"); bool useContourMap = args.read("--contourmap"); if (args.read("--verbose")) osgEarth::setNotifyLevel(osg::INFO); if (args.read("--quiet")) osgEarth::setNotifyLevel(osg::FATAL); float ambientBrightness = 0.2f; args.read("--ambientBrightness", ambientBrightness); std::string kmlFile; args.read( "--kml", kmlFile ); std::string imageFolder; args.read( "--images", imageFolder ); std::string imageExtensions; args.read("--image-extensions", imageExtensions); // animation path: std::string animpath; if ( args.read("--path", animpath) ) { view->setCameraManipulator( new osgGA::AnimationPathManipulator(animpath) ); } // Install a new Canvas for our UI controls, or use one that already exists. ControlCanvas* canvas = ControlCanvas::getOrCreate( view ); Container* mainContainer; if ( userContainer ) { mainContainer = userContainer; } else { mainContainer = new VBox(); mainContainer->setAbsorbEvents( true ); mainContainer->setBackColor( Color(Color::Black, 0.8) ); mainContainer->setHorizAlign( Control::ALIGN_LEFT ); mainContainer->setVertAlign( Control::ALIGN_BOTTOM ); } canvas->addControl( mainContainer ); // Add an event handler to toggle the canvas with a key press; view->addEventHandler(new ToggleCanvasEventHandler(canvas) ); // look for external data in the map node: const Config& externals = mapNode->externalConfig(); const Config& skyConf = externals.child("sky"); const Config& oceanConf = externals.child("ocean"); const Config& screenSpaceLayoutConf = externals.hasChild("screen_space_layout") ? externals.child("screen_space_layout") : externals.child("decluttering"); // backwards-compatibility // some terrain effects. // TODO: Most of these are likely to move into extensions. const Config& lodBlendingConf = externals.child("lod_blending"); const Config& vertScaleConf = externals.child("vertical_scale"); const Config& contourMapConf = externals.child("contour_map"); // Adding a sky model: if ( useSky || !skyConf.empty() ) { SkyOptions options(skyConf); if ( options.getDriver().empty() ) { if ( mapNode->getMapSRS()->isGeographic() ) options.setDriver("simple"); else options.setDriver("gl"); } SkyNode* sky = SkyNode::create(options, mapNode); if ( sky ) { sky->attach( view, 0 ); if ( mapNode->getNumParents() > 0 ) { osgEarth::insertGroup(sky, mapNode->getParent(0)); } else { sky->addChild( mapNode ); root = sky; } Control* c = SkyControlFactory().create(sky, view); if ( c ) mainContainer->addControl( c ); if (animateSky) { sky->setUpdateCallback( new AnimateSkyUpdateCallback() ); } } } // Adding an ocean model: if ( useOcean || !oceanConf.empty() ) { OceanNode* ocean = OceanNode::create(OceanOptions(oceanConf), mapNode); if ( ocean ) { // if there's a sky, we want to ocean under it osg::Group* parent = osgEarth::findTopMostNodeOfType<SkyNode>(root); if ( !parent ) parent = root; parent->addChild( ocean ); Control* c = OceanControlFactory().create(ocean); if ( c ) mainContainer->addControl(c); } } // Shadowing. if ( useShadows ) { int unit; if ( mapNode->getTerrainEngine()->getResources()->reserveTextureImageUnit(unit, "ShadowCaster") ) { ShadowCaster* caster = new ShadowCaster(); caster->setTextureImageUnit( unit ); caster->setLight( view->getLight() ); caster->getShadowCastingGroup()->addChild( mapNode ); //->getModelLayerGroup() ); if ( mapNode->getNumParents() > 0 ) { insertGroup(caster, mapNode->getParent(0)); } else { caster->addChild(mapNode); root = caster; } } } // Loading KML from the command line: if ( !kmlFile.empty() ) { KMLOptions kml_options; kml_options.declutter() = true; // set up a default icon for point placemarks: IconSymbol* defaultIcon = new IconSymbol(); defaultIcon->url()->setLiteral(KML_PUSHPIN_URL); kml_options.defaultIconSymbol() = defaultIcon; TextSymbol* defaultText = new TextSymbol(); defaultText->halo() = Stroke(0.3,0.3,0.3,1.0); kml_options.defaultTextSymbol() = defaultText; osg::Node* kml = KML::load( URI(kmlFile), mapNode, kml_options ); if ( kml ) { if (kmlUI) { Control* c = AnnotationGraphControlFactory().create(kml, view); if ( c ) { c->setVertAlign( Control::ALIGN_TOP ); canvas->addControl( c ); } } root->addChild( kml ); } else { OE_NOTICE << "Failed to load " << kmlFile << std::endl; } } // Configure the de-cluttering engine for labels and annotations: if ( !screenSpaceLayoutConf.empty() ) { ScreenSpaceLayout::setOptions( ScreenSpaceLayoutOptions(screenSpaceLayoutConf) ); } // Configure the mouse coordinate readout: if ( useCoords ) { LabelControl* readout = new LabelControl(); readout->setBackColor( Color(Color::Black, 0.8) ); readout->setHorizAlign( Control::ALIGN_RIGHT ); readout->setVertAlign( Control::ALIGN_BOTTOM ); Formatter* formatter = useMGRS ? (Formatter*)new MGRSFormatter(MGRSFormatter::PRECISION_1M, 0L, MGRSFormatter::USE_SPACES) : useDMS ? (Formatter*)new LatLongFormatter(LatLongFormatter::FORMAT_DEGREES_MINUTES_SECONDS) : useDD ? (Formatter*)new LatLongFormatter(LatLongFormatter::FORMAT_DECIMAL_DEGREES) : 0L; MouseCoordsTool* mcTool = new MouseCoordsTool( mapNode ); mcTool->addCallback( new MouseCoordsLabelCallback(readout, formatter) ); view->addEventHandler( mcTool ); canvas->addControl( readout ); } // Configure for an ortho camera: if ( useOrtho ) { view->getCamera()->setProjectionMatrixAsOrtho(-1, 1, -1, 1, 0, 1); } // activity monitor (debugging) if ( showActivity ) { VBox* vbox = new VBox(); vbox->setBackColor( Color(Color::Black, 0.8) ); vbox->setHorizAlign( Control::ALIGN_RIGHT ); vbox->setVertAlign( Control::ALIGN_BOTTOM ); view->addEventHandler( new ActivityMonitorTool(vbox) ); canvas->addControl( vbox ); } // Install an auto clip plane clamper if ( useAutoClip ) { mapNode->addCullCallback( new AutoClipPlaneCullCallback(mapNode) ); } // Install logarithmic depth buffer on main camera if ( useLogDepth ) { OE_INFO << LC << "Activating logarithmic depth buffer (vertex-only) on main camera" << std::endl; osgEarth::Util::LogarithmicDepthBuffer logDepth; logDepth.setUseFragDepth( false ); logDepth.install( view->getCamera() ); } else if ( useLogDepth2 ) { OE_INFO << LC << "Activating logarithmic depth buffer (precise) on main camera" << std::endl; osgEarth::Util::LogarithmicDepthBuffer logDepth; logDepth.setUseFragDepth( true ); logDepth.install( view->getCamera() ); } // Scan for images if necessary. if ( !imageFolder.empty() ) { std::vector<std::string> extensions; if ( !imageExtensions.empty() ) StringTokenizer( imageExtensions, extensions, ",;", "", false, true ); if ( extensions.empty() ) extensions.push_back( "tif" ); OE_INFO << LC << "Loading images from " << imageFolder << "..." << std::endl; ImageLayerVector imageLayers; DataScanner scanner; scanner.findImageLayers( imageFolder, extensions, imageLayers ); if ( imageLayers.size() > 0 ) { mapNode->getMap()->beginUpdate(); for( ImageLayerVector::iterator i = imageLayers.begin(); i != imageLayers.end(); ++i ) { mapNode->getMap()->addImageLayer( i->get() ); } mapNode->getMap()->endUpdate(); } OE_INFO << LC << "...found " << imageLayers.size() << " image layers." << std::endl; } // Install elevation morphing if ( !lodBlendingConf.empty() ) { mapNode->getTerrainEngine()->addEffect( new LODBlending(lodBlendingConf) ); } // Install vertical scaler if ( !vertScaleConf.empty() ) { mapNode->getTerrainEngine()->addEffect( new VerticalScale(vertScaleConf) ); } // Install a contour map effect. if ( !contourMapConf.empty() || useContourMap ) { mapNode->getTerrainEngine()->addEffect( new ContourMap(contourMapConf) ); // with the cmdline switch, hids all the image layer so we can see the contour map. if (useContourMap) { for (unsigned i = 0; i < mapNode->getMap()->getNumImageLayers(); ++i) { mapNode->getMap()->getImageLayerAt(i)->setVisible(false); } } } // Generic named value uniform with min/max. VBox* uniformBox = 0L; while( args.find( "--uniform" ) >= 0 ) { std::string name; float minval, maxval; if ( args.read( "--uniform", name, minval, maxval ) ) { if ( uniformBox == 0L ) { uniformBox = new VBox(); uniformBox->setBackColor(0,0,0,0.5); uniformBox->setAbsorbEvents( true ); canvas->addControl( uniformBox ); } osg::Uniform* uniform = new osg::Uniform(osg::Uniform::FLOAT, name); uniform->set( minval ); root->getOrCreateStateSet()->addUniform( uniform, osg::StateAttribute::OVERRIDE ); HBox* box = new HBox(); box->addControl( new LabelControl(name) ); HSliderControl* hs = box->addControl( new HSliderControl(minval, maxval, minval, new ApplyValueUniform(uniform))); hs->setHorizFill(true, 200); box->addControl( new LabelControl(hs) ); uniformBox->addControl( box ); OE_INFO << LC << "Installed uniform controller for " << name << std::endl; } } if ( inspect ) { mapNode->addExtension( Extension::create("mapinspector", ConfigOptions()) ); } // Process extensions. for(std::vector<osg::ref_ptr<Extension> >::const_iterator eiter = mapNode->getExtensions().begin(); eiter != mapNode->getExtensions().end(); ++eiter) { Extension* e = eiter->get(); // Check for a View interface: ExtensionInterface<osg::View>* viewIF = ExtensionInterface<osg::View>::get( e ); if ( viewIF ) viewIF->connect( view ); // Check for a Control interface: ExtensionInterface<Control>* controlIF = ExtensionInterface<Control>::get( e ); if ( controlIF ) controlIF->connect( mainContainer ); } root->addChild( canvas ); }
int show(osg::ArgumentParser& arguments) { // find the resource library file: std::string inCatalogFile; if ( !arguments.read("--show", inCatalogFile) ) return usage("Missing required catalog file name"); int layer = 0; arguments.read("--layer", layer); bool drawLabels; drawLabels = arguments.read("--labels"); std::string auxPattern; arguments.read("--aux", auxPattern); // open the resource library: osg::ref_ptr<osgEarth::Symbology::ResourceLibrary> lib = new osgEarth::Symbology::ResourceLibrary("temp", osgEarth::URI(inCatalogFile) ); if ( lib->initialize(0L) == false ) return usage("Failed to load resource catalog"); // the atlas name is the library name without the extension. Not strictly true // but true if you didn't rename it :) std::string atlasFile = osgDB::getNameLessExtension(inCatalogFile); // check for an auxiliary pattern: if ( !auxPattern.empty() ) { atlasFile = osgDB::getNameLessExtension(atlasFile) + "_" + auxPattern + "." + osgDB::getFileExtension(atlasFile); } osg::Image* image = osgDB::readImageFile(atlasFile); if ( !image ) return usage("Failed to load atlas image"); if ( layer > image->r()-1 ) return usage("Specified layer does not exist"); // geometry for the image layer: std::vector<osg::ref_ptr<osg::Image> > images; osgEarth::ImageUtils::flattenImage(image, images); osg::Geode* geode = osg::createGeodeForImage(images[layer].get()); // geometry for the skins in that layer: osg::Geode* geode2 = new osg::Geode(); osg::Geometry* geom = new osg::Geometry(); geode2->addDrawable(geom); osg::Vec3Array* v = new osg::Vec3Array(); geom->setVertexArray( v ); osg::Vec4Array* c = new osg::Vec4Array(1); (*c)[0].set(1,1,0,1); geom->setColorArray(c); geom->setColorBinding(geom->BIND_OVERALL); osgEarth::Symbology::SkinResourceVector skins; lib->getSkins(skins); for(unsigned k=0; k<skins.size(); ++k) { if (skins[k]->imageLayer() == layer && skins[k]->isTiled() == false) { float x = -1.0f + 2.0*skins[k]->imageBiasS().value(); float y = -1.0f + 2.0*skins[k]->imageBiasT().value(); float s = 2.0*skins[k]->imageScaleS().value(); float t = 2.0*skins[k]->imageScaleT().value(); v->push_back(osg::Vec3(x, -0.01f, y )); v->push_back(osg::Vec3(x + s, -0.01f, y )); v->push_back(osg::Vec3(x + s, -0.01f, y + t)); v->push_back(osg::Vec3(x, -0.01f, y + t)); geom->addPrimitiveSet(new osg::DrawArrays(GL_LINE_LOOP, v->size()-4, 4)); if (drawLabels) { osgText::Text* label = new osgText::Text(); label->setText(skins[k]->name()); label->setPosition(osg::Vec3(x+0.5*s, -0.005f, y+0.5*t)); label->setAlignment(label->CENTER_CENTER); label->setAutoRotateToScreen(true); label->setCharacterSizeMode(label->SCREEN_COORDS); label->setCharacterSize(20.0f); label->setFont("arialbd.ttf"); geode2->addDrawable(label); } } } osg::Group* root = new osg::Group(); root->addChild( geode ); root->addChild( geode2 ); root->getOrCreateStateSet()->setMode(GL_LIGHTING, 0); root->getOrCreateStateSet()->setMode(GL_CULL_FACE, 0); osgViewer::Viewer viewer; viewer.setSceneData( root ); viewer.addEventHandler(new osgViewer::StatsHandler()); viewer.run(); return 0; }
CefRefPtr<BrowserClient> CefHelper::load(osg::ArgumentParser& args, const std::string& htmlFile) { // Initialize CEF CefMainArgs cef_args; CefRefPtr<CefApp> cef_app = new OECefApp(); int exitCode = CefExecuteProcess(cef_args, cef_app, 0L); if (exitCode >= 0) { return 0L; } { CefSettings settings; if (getenv("CEF_RESOURCES_DIR") != 0) CefString(&settings.resources_dir_path) = getenv("CEF_RESOURCES_DIR"); if (getenv("CEF_LOCALES_DIR") != 0) CefString(&settings.locales_dir_path) = getenv("CEF_LOCALES_DIR"); settings.windowless_rendering_enabled = true; bool result = CefInitialize(cef_args, settings, cef_app, 0L); if (!result) { OE_WARN << LC << "CefInitialize failed." << std::endl; return 0L; } } // Read in the html file if needed std::string url = ""; if (htmlFile.length() > 0) { url = htmlFile; } else { if (!args.read("--url", url)) { for( int i=0; i<args.argc(); ++i ) { if ( osgDB::getLowerCaseFileExtension(args[i]) == "html" ) { url = args[i]; args.remove(i); break; } } } } // No file specified, try the default index.html if (url.length() == 0) url = osgDB::getRealPath("index.html"); // No file specified and index.html does not exist so exit if (url.length() == 0) { OE_WARN << LC << "No html file specified, exiting..." << std::endl; return 0L; } // A file or url was specified so get the full address std::string fullPath = osgDB::containsServerAddress(url) ? url : osgDB::getRealPath(url); // Setup a CompositeViewer osg::ref_ptr<osgViewer::CompositeViewer> viewer = new osgViewer::CompositeViewer(args); viewer->setThreadingModel(osgViewer::Viewer::SingleThreaded); // prevents "ESC" from killing the application viewer->setKeyEventSetsDone( 0 ); viewer->setQuitEventSetsDone( false ); // Create the BrowserClient CefRefPtr<BrowserClient> browserClient = new BrowserClient(viewer.get(), fullPath, 1024, 768); return browserClient; }
osg::ref_ptr<osg::Node> p3d::readShowFiles(osg::ArgumentParser& arguments,const osgDB::ReaderWriter::Options* options) { osg::ref_ptr<osgDB::Options> local_options = createOptions(options); local_options->setOptionString("main"); typedef std::vector< osg::ref_ptr<osg::Node> > NodeList; NodeList nodeList; std::string filename; while (arguments.read("--image",filename)) { osg::ref_ptr<osg::Image> image = readImageFile(filename.c_str(), local_options.get()); if (image.valid()) nodeList.push_back(osg::createGeodeForImage(image.get())); } while (arguments.read("--movie",filename)) { osg::ref_ptr<osg::Image> image = readImageFile(filename.c_str(), local_options.get()); osg::ref_ptr<osg::ImageStream> imageStream = dynamic_cast<osg::ImageStream*>(image.get()); if (image.valid()) { imageStream->play(); nodeList.push_back(osg::createGeodeForImage(imageStream.get())); } } while (arguments.read("--dem",filename)) { osg::HeightField* hf = readHeightFieldFile(filename.c_str(), local_options.get()); if (hf) { osg::Geode* geode = new osg::Geode; geode->addDrawable(new osg::ShapeDrawable(hf)); nodeList.push_back(geode); } } // note currently doesn't delete the loaded file entries from the command line yet... for(int pos=1;pos<arguments.argc();++pos) { if (!arguments.isOption(pos)) { // not an option so assume string is a filename. osg::Node *node = osgDB::readNodeFile( arguments[pos], local_options.get()); if(node) { if (node->getName().empty()) node->setName( arguments[pos] ); nodeList.push_back(node); } } } if (nodeList.empty()) { return NULL; } osg::ref_ptr<osg::Node> root; if (nodeList.size()==1) { root = nodeList.front().get(); } else // size >1 { osg::Switch* sw = new osg::Switch; for(NodeList::iterator itr=nodeList.begin(); itr!=nodeList.end(); ++itr) { sw->addChild((*itr).get()); } sw->setSingleChildOn(0); sw->setEventCallback(new p3d::ShowEventHandler()); root = sw; } if (root.valid()) { osg::notify(osg::INFO)<<"Got node now adding callback"<<std::endl; AddVolumeEditingCallbackVisitor avecv; root->accept(avecv); } return root; }
void ossimPlanetQtApplication::addCommandLineOptions(osg::ArgumentParser& args) { args.getApplicationUsage()->setApplicationName(args.getApplicationName()); args.getApplicationUsage()->setDescription(args.getApplicationName()+" is the test application for accessing wms servers."); args.getApplicationUsage()->setCommandLineUsage(args.getApplicationName()+" [options] ..."); args.getApplicationUsage()->addCommandLineOption("-h or --help","Display this information"); args.getApplicationUsage()->addCommandLineOption("--enable-flatland", "Uses the flat land model"); args.getApplicationUsage()->addCommandLineOption("--disable-elevation", "Uses elevation"); args.getApplicationUsage()->addCommandLineOption("--elev-estimation", "number of levels to estimate. A value of 4 will say 2^4 or 16 number of rows and cols."); args.getApplicationUsage()->addCommandLineOption("--split-metric", "set Split Metric Ratio. Default is 3.0"); args.getApplicationUsage()->addCommandLineOption("--elev-patchsize", "number of points in each chunk."); args.getApplicationUsage()->addCommandLineOption("--elev-exag", "Multiplier for the height values"); args.getApplicationUsage()->addCommandLineOption("--elev-cache", "Cache directory for elevation"); args.getApplicationUsage()->addCommandLineOption("--level-detail", "Maximum level of detail to split to. Default is 16 levels"); args.getApplicationUsage()->addCommandLineOption("--enable-hud", "Enables the lat lon read outs"); args.getApplicationUsage()->addCommandLineOption("--disable-hud", "Disable the lat lon read outs"); args.getApplicationUsage()->addCommandLineOption("--disable-mipmap", "Doesn't use MipMapping"); args.getApplicationUsage()->addCommandLineOption("--enable-mipmap", "Use MipMapping"); args.getApplicationUsage()->addCommandLineOption("--wms-timeout", "Time out for WMS get Capabiltites for the WmsDialog specified in seconds"); }