root/OpenSceneGraph/trunk/examples/osganalysis/osganalysis.cpp @ 12031

Revision 12031, 24.4 kB (checked in by robert, 4 years ago)

Improved the parsing of output filename

Line 
1/* OpenSceneGraph example, osgterrain.
2*
3*  Permission is hereby granted, free of charge, to any person obtaining a copy
4*  of this software and associated documentation files (the "Software"), to deal
5*  in the Software without restriction, including without limitation the rights
6*  to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
7*  copies of the Software, and to permit persons to whom the Software is
8*  furnished to do so, subject to the following conditions:
9*
10*  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
11*  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
12*  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
13*  AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
14*  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
15*  OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
16*  THE SOFTWARE.
17*/
18
19
20#include <osgViewer/Viewer>
21#include <osgViewer/ViewerEventHandlers>
22
23#include <osgDB/ReadFile>
24#include <osgDB/WriteFile>
25#include <osgDB/FileNameUtils>
26
27#include <osgGA/TrackballManipulator>
28#include <osgGA/StateSetManipulator>
29#include <osgGA/TrackballManipulator>
30#include <osgGA/FlightManipulator>
31#include <osgGA/DriveManipulator>
32#include <osgGA/KeySwitchMatrixManipulator>
33#include <osgGA/AnimationPathManipulator>
34#include <osgGA/TerrainManipulator>
35
36#include <osgUtil/IncrementalCompileOperation>
37#include <osgUtil/Simplifier>
38#include <osgUtil/MeshOptimizers>
39
40class StripStateVisitor : public osg::NodeVisitor
41{
42public:
43    StripStateVisitor(bool useStateSets, bool useDisplayLists, bool useVBO):
44        osg::NodeVisitor(osg::NodeVisitor::TRAVERSE_ALL_CHILDREN),
45        _useStateSets(useStateSets),
46        _useDisplayLists(useDisplayLists),
47        _useVBO(useVBO) {}
48
49    bool _useStateSets;
50    bool _useDisplayLists;
51    bool _useVBO;
52
53    void apply(osg::Node& node)
54    {
55        if (!_useStateSets && node.getStateSet()) node.setStateSet(0);
56        traverse(node);
57    }
58
59    void apply(osg::Geode& node)
60    {
61        if (!_useStateSets && node.getStateSet()) node.setStateSet(0);
62        for(unsigned int i = 0; i<node.getNumDrawables(); ++i)
63        {
64            process(*node.getDrawable(i));
65        }
66
67        traverse(node);
68    }
69
70    void process(osg::Drawable& drawable)
71    {
72        if (!_useStateSets && drawable.getStateSet())
73        {
74            drawable.setStateSet(0);
75        }
76
77        drawable.setUseDisplayList(_useDisplayLists);
78        drawable.setUseVertexBufferObjects(_useVBO);
79    }
80};
81
82class SwapArrayVisitor : public osg::ArrayVisitor
83{
84public:
85    SwapArrayVisitor(osg::Array* array):
86        _array(array) {}
87
88    template <class ARRAY>
89    void apply_imp(ARRAY& array)
90    {
91        if (array.getType()!=_array->getType())
92        {
93            OSG_NOTICE<<"Arrays incompatible"<<std::endl;
94            return;
95        }
96        OSG_NOTICE<<"Swapping Array"<<std::endl;
97        array.swap(*static_cast<ARRAY*>(_array));
98    }
99
100    virtual void apply(osg::ByteArray& ba) { apply_imp(ba); }
101    virtual void apply(osg::ShortArray& ba) { apply_imp(ba); }
102    virtual void apply(osg::IntArray& ba) { apply_imp(ba); }
103    virtual void apply(osg::UByteArray& ba) { apply_imp(ba); }
104    virtual void apply(osg::UShortArray& ba) { apply_imp(ba); }
105    virtual void apply(osg::UIntArray& ba) { apply_imp(ba); }
106    virtual void apply(osg::Vec4ubArray& ba) { apply_imp(ba); }
107    virtual void apply(osg::FloatArray& ba) { apply_imp(ba); }
108    virtual void apply(osg::Vec2Array& ba) { apply_imp(ba); }
109    virtual void apply(osg::Vec3Array& ba) { apply_imp(ba); }
110    virtual void apply(osg::Vec4Array& ba) { apply_imp(ba); }
111
112    osg::Array* _array;
113};
114
115class MemoryVisitor : public osg::NodeVisitor
116{
117public:
118     MemoryVisitor():
119         osg::NodeVisitor(osg::NodeVisitor::TRAVERSE_ALL_CHILDREN) {}
120
121
122    void reset()
123    {
124         _nodes.clear();
125         _geometryMap.clear();
126         _arrayMap.clear();
127         _primitiveSetMap.clear();
128    }
129
130    void apply(osg::Node& node)
131    {
132        _nodes.insert(&node);
133        traverse(node);
134    }
135
136    void apply(osg::Geode& geode)
137    {
138        _nodes.insert(&geode);
139        for(unsigned int i=0; i<geode.getNumDrawables(); ++i)
140        {
141            apply(&geode, geode.getDrawable(i));
142        }
143    }
144
145    void apply(osg::Geode* geode, osg::Drawable* drawable)
146    {
147        if (!drawable) return;
148
149        osg::Geometry* geometry = drawable->asGeometry();
150        if (geometry)
151        {
152            _geometryMap[geometry].insert(geode);
153
154            apply(geometry, geometry->getVertexArray());
155            apply(geometry, geometry->getNormalArray());
156            apply(geometry, geometry->getColorArray());
157            apply(geometry, geometry->getSecondaryColorArray());
158            apply(geometry, geometry->getFogCoordArray());
159
160            for(unsigned int i=0; i<geometry->getNumTexCoordArrays(); ++i)
161            {
162                apply(geometry, geometry->getTexCoordArray(i));
163            }
164            for(unsigned int i=0; i<geometry->getNumVertexAttribArrays(); ++i)
165            {
166                apply(geometry, geometry->getVertexAttribArray(i));
167            }
168
169            for(unsigned int i=0; i<geometry->getNumPrimitiveSets(); ++i)
170            {
171                apply(geometry, geometry->getPrimitiveSet(i));
172            }
173        }
174    }
175
176    void apply(osg::Geometry* geometry, osg::Array* array)
177    {
178        if (!array) return;
179        _arrayMap[array].insert(geometry);
180    }
181
182    void apply(osg::Geometry* geometry, osg::PrimitiveSet* primitiveSet)
183    {
184        if (!primitiveSet) return;
185        _primitiveSetMap[primitiveSet].insert(geometry);
186    }
187
188    void report(std::ostream& out)
189    {
190        OSG_NOTICE<<"Nodes "<<_nodes.size()<<std::endl;
191        OSG_NOTICE<<"Geometries "<<_geometryMap.size()<<std::endl;
192        OSG_NOTICE<<"Arrays "<<_arrayMap.size()<<std::endl;
193        OSG_NOTICE<<"PrimitiveSets "<<_primitiveSetMap.size()<<std::endl;
194    }
195
196    void reallocate()
197    {
198        OSG_NOTICE<<"Reallocating Arrays"<<std::endl;
199
200        typedef std::vector< osg::ref_ptr<osg::Array> > ArrayVector;
201        typedef std::vector< osg::ref_ptr<osg::Geometry> > GeometryVector;
202        ArrayVector newArrays;
203        GeometryVector newGeometries;
204        for(GeometryMap::iterator itr = _geometryMap.begin();
205            itr != _geometryMap.end();
206            ++itr)
207        {
208            osg::Geometry* geometry = itr->first;
209            bool useVBO = geometry->getUseVertexBufferObjects();
210            osg::Geometry* newGeometry = osg::clone(geometry, osg::CopyOp(osg::CopyOp::DEEP_COPY_ALL));
211            newGeometry->setUseVertexBufferObjects(false);
212            newGeometry->setUseVertexBufferObjects(useVBO);
213            newGeometries.push_back(newGeometry);
214        }
215
216        GeometryVector::iterator geom_itr = newGeometries.begin();
217        for(GeometryMap::iterator itr = _geometryMap.begin();
218            itr != _geometryMap.end();
219            ++itr, ++geom_itr)
220        {
221            osg::Geometry* geometry = itr->first;
222            Geodes& geodes = itr->second;
223            for(Geodes::iterator gitr = geodes.begin();
224                gitr != geodes.end();
225                ++gitr)
226            {
227                osg::Geode* geode = const_cast<osg::Geode*>(*gitr);
228                geode->replaceDrawable(geometry, geom_itr->get());
229            }
230        }
231    }
232
233    typedef std::vector< osg::ref_ptr<osg::Geometry> > GeometryVector;
234    typedef std::pair<osg::Array*, osg::Array*> ArrayPair;
235    typedef std::vector< ArrayPair > ArrayVector;
236    typedef std::pair<osg::PrimitiveSet*, osg::PrimitiveSet*> PrimitiveSetPair;
237    typedef std::vector< PrimitiveSetPair > PrimitiveSetVector;
238
239    osg::Array* cloneArray(ArrayVector& arrayVector, osg::Array* array)
240    {
241        if (!array) return 0;
242        osg::Array* newArray = static_cast<osg::Array*>(array->cloneType());
243        arrayVector.push_back(ArrayPair(array,newArray));
244        return newArray;
245    }
246
247    osg::PrimitiveSet* clonePrimitiveSet(PrimitiveSetVector& psVector, osg::PrimitiveSet* ps)
248    {
249        if (!ps) return 0;
250        osg::PrimitiveSet* newPS = static_cast<osg::PrimitiveSet*>(ps->cloneType());
251        psVector.push_back(PrimitiveSetPair(ps,newPS));
252        return newPS;
253    }
254
255    void reallocate2()
256    {
257        OSG_NOTICE<<"Reallocating Arrays"<<std::endl;
258
259        ArrayVector arrayVector;
260        PrimitiveSetVector primitiveSetVector;
261        GeometryVector newGeometries;
262
263        for(GeometryMap::iterator itr = _geometryMap.begin();
264            itr != _geometryMap.end();
265            ++itr)
266        {
267            osg::Geometry* geometry = itr->first;
268            osg::ref_ptr<osg::Geometry> newGeometry = osg::clone(geometry, osg::CopyOp::SHALLOW_COPY);
269            newGeometries.push_back(newGeometry.get());
270
271            newGeometry->setVertexArray(cloneArray(arrayVector, geometry->getVertexArray()));
272            newGeometry->setNormalArray(cloneArray(arrayVector, geometry->getNormalArray()));
273            newGeometry->setColorArray(cloneArray(arrayVector, geometry->getColorArray()));
274            newGeometry->setSecondaryColorArray(cloneArray(arrayVector, geometry->getSecondaryColorArray()));
275            newGeometry->setFogCoordArray(cloneArray(arrayVector, geometry->getFogCoordArray()));
276            for(unsigned int i=0; i<geometry->getNumTexCoordArrays(); ++i)
277            {
278                newGeometry->setTexCoordArray(i, cloneArray(arrayVector, geometry->getTexCoordArray(i)));
279            }
280            for(unsigned int i=0; i<geometry->getNumVertexAttribArrays(); ++i)
281            {
282                newGeometry->setVertexAttribArray(i, cloneArray(arrayVector, geometry->getVertexAttribArray(i)));
283            }
284
285            for(unsigned int i=0; i<geometry->getNumPrimitiveSets(); ++i)
286            {
287                newGeometry->setPrimitiveSet(i,clonePrimitiveSet(primitiveSetVector, geometry->getPrimitiveSet(i)));
288            }
289        }
290
291        GeometryVector::iterator geom_itr = newGeometries.begin();
292        for(GeometryMap::iterator itr = _geometryMap.begin();
293            itr != _geometryMap.end();
294            ++itr, ++geom_itr)
295        {
296            osg::Geometry* geometry = itr->first;
297            Geodes& geodes = itr->second;
298            for(Geodes::iterator gitr = geodes.begin();
299                gitr != geodes.end();
300                ++gitr)
301            {
302                osg::Geode* geode = const_cast<osg::Geode*>(*gitr);
303                geode->replaceDrawable(geometry, geom_itr->get());
304            }
305        }
306    }
307
308protected:
309
310     typedef std::set<osg::Node*>  Nodes;
311     typedef std::set<osg::Geode*>  Geodes;
312     typedef std::set<osg::Geometry*>  Geometries;
313     typedef std::map<osg::Geometry*, Geodes> GeometryMap;
314     typedef std::map<osg::Array*, Geometries> ArrayMap;
315     typedef std::map<osg::PrimitiveSet*, Geometries> PrimitiveSetMap;
316
317     Nodes              _nodes;
318     GeometryMap        _geometryMap;
319     ArrayMap           _arrayMap;
320     PrimitiveSetMap    _primitiveSetMap;
321};
322
323class SceneGraphProcessor : public osg::Referenced
324{
325public:
326    SceneGraphProcessor()
327    {
328        _init();
329    }
330
331    SceneGraphProcessor(osg::ArgumentParser& arguments)
332    {
333        _init();
334
335        while (arguments.read("--vbo")) { modifyDrawableSettings = true; useVBO = true;  }
336        while (arguments.read("--dl")) { modifyDrawableSettings = true; useDisplayLists = true;  }
337
338        while (arguments.read("-s", simplificatioRatio)) {}
339        while (arguments.read("--tristripper")) { useTriStripVisitor=true; }
340        while (arguments.read("--no-tristripper")) { useTriStripVisitor=false; }
341        while (arguments.read("--smoother")) {  useSmoothingVisitor=true; }
342        while (arguments.read("--no-smoother")) {  useSmoothingVisitor=false; }
343
344        while (arguments.read("--remove-duplicate-vertices") || arguments.read("--rdv")) removeDuplicateVertices = true;
345        while (arguments.read("--optimize-vertex-cache") || arguments.read("--ovc")) optimizeVertexCache = true;
346        while (arguments.read("--optimize-vertex-order") || arguments.read("--ovo")) optimizeVertexOrder = true;
347
348        while (arguments.read("--build-mipmaps")) { modifyTextureSettings = true; buildImageMipmaps = true; }
349        while (arguments.read("--compress")) { modifyTextureSettings = true; compressImages = true; }
350        while (arguments.read("--disable-mipmaps")) { modifyTextureSettings = true; disableMipmaps = true; }
351
352        while (arguments.read("--reallocate") || arguments.read("--ra") ) { reallocateMemory = true; }
353
354
355        OSG_NOTICE<<"simplificatioRatio="<<simplificatioRatio<<std::endl;
356    }
357
358    virtual osg::Node* process(osg::Node* node)
359    {
360        if (!node)
361        {
362            OSG_NOTICE<<"SceneGraphProcessor::process(Node*) : error cannot process NULL Node."<<std::endl;
363            return 0;
364        }
365
366        OSG_NOTICE<<"SceneGraphProcessor::process("<<node<<") : "<<node->getName()<<std::endl;
367
368        if (simplificatioRatio < 1.0)
369        {
370            OSG_NOTICE<<"Running simplifier with simplification ratio="<<simplificatioRatio<<std::endl;
371            float maxError = 4.0f;
372            osgUtil::Simplifier simplifier(simplificatioRatio, maxError);
373            simplifier.setDoTriStrip(useTriStripVisitor);
374            simplifier.setSmoothing(useSmoothingVisitor);
375            node->accept(simplifier);
376        }
377
378        if (removeDuplicateVertices)
379        {
380            OSG_NOTICE<<"Running osgUtil::IndexMeshVisitor"<<std::endl;
381            osgUtil::IndexMeshVisitor imv;
382            node->accept(imv);
383            imv.makeMesh();
384        }
385
386        if (optimizeVertexCache)
387        {
388            OSG_NOTICE<<"Running osgUtil::VertexCacheVisitor"<<std::endl;
389            osgUtil::VertexCacheVisitor vcv;
390            node->accept(vcv);
391            vcv.optimizeVertices();
392        }
393
394        if (optimizeVertexOrder)
395        {
396            OSG_NOTICE<<"Running osgUtil::VertexAccessOrderVisitor"<<std::endl;
397            osgUtil::VertexAccessOrderVisitor vaov;
398            node->accept(vaov);
399            vaov.optimizeOrder();
400        }
401
402        if (modifyDrawableSettings || modifyTextureSettings)
403        {
404            OSG_NOTICE<<"Running StripStateVisitor"<<std::endl;
405            StripStateVisitor ssv(true, useDisplayLists, useVBO);
406            node->accept(ssv);
407        }
408
409        MemoryVisitor mv;
410        node->accept(mv);
411        mv.report(osg::notify(osg::NOTICE));
412
413        if (reallocateMemory)
414        {
415            OSG_NOTICE<<"Running Reallocation of scene graph memory"<<std::endl;
416            mv.reallocate();
417        }
418
419        mv.reset();
420        node->accept(mv);
421        mv.report(osg::notify(osg::NOTICE));
422
423        return node;
424    }
425
426protected:
427
428    void _init()
429    {
430        modifyDrawableSettings = false;
431        useVBO = false;
432        useDisplayLists = false;
433
434        simplificatioRatio = 1.0;
435        useTriStripVisitor = false;
436        useSmoothingVisitor = false;
437
438        removeDuplicateVertices = false;
439        optimizeVertexCache = false;
440        optimizeVertexOrder = false;
441
442        reallocateMemory = false;
443       
444        modifyTextureSettings = false;
445        buildImageMipmaps = false;
446        compressImages = false;
447        disableMipmaps = false;
448    }
449
450    bool modifyDrawableSettings;
451    bool useVBO;
452    bool useDisplayLists;
453
454    float simplificatioRatio;
455    bool useTriStripVisitor;
456    bool useSmoothingVisitor;
457
458    bool removeDuplicateVertices;
459    bool optimizeVertexCache;
460    bool optimizeVertexOrder;
461
462    bool reallocateMemory;
463   
464    bool modifyTextureSettings;
465    bool buildImageMipmaps;
466    bool compressImages;
467    bool disableMipmaps;
468
469};
470
471class DatabasePagingOperation : public osg::Operation, public osgUtil::IncrementalCompileOperation::CompileCompletedCallback
472{
473public:
474
475    DatabasePagingOperation(const std::string& filename,
476                            const std::string& outputFilename,
477                             SceneGraphProcessor* sceneGraphProcessor,
478                             osgUtil::IncrementalCompileOperation* ico):
479        Operation("DatabasePaging Operation", false),
480        _filename(filename),
481        _outputFilename(outputFilename),
482        _modelReadyToMerge(false),
483        _sceneGraphProcessor(sceneGraphProcessor),
484        _incrementalCompileOperation(ico)
485        {
486        }
487
488    virtual void operator () (osg::Object* object)
489    {
490        osg::notify(osg::NOTICE)<<"LoadAndCompileOperation "<<_filename<<std::endl;
491
492        _modelReadyToMerge = false;
493        _loadedModel = osgDB::readNodeFile(_filename);
494
495        if (_loadedModel.valid())
496        {
497            if (_sceneGraphProcessor.valid())
498            {
499                _loadedModel = _sceneGraphProcessor->process(_loadedModel.get());
500            }
501        }
502
503        if (_loadedModel.valid())
504        {
505            if (!_outputFilename.empty())
506            {
507                OSG_NOTICE<<"Writing out file "<<_outputFilename<<std::endl;
508               
509                osgDB::writeNodeFile(*_loadedModel, _outputFilename);
510            }
511
512            if (_incrementalCompileOperation.valid())
513            {
514                osg::ref_ptr<osgUtil::IncrementalCompileOperation::CompileSet> compileSet =
515                    new osgUtil::IncrementalCompileOperation::CompileSet(_loadedModel.get());
516
517                compileSet->_compileCompletedCallback = this;
518
519                _incrementalCompileOperation->add(compileSet.get());
520            }
521            else
522            {
523                _modelReadyToMerge = true;
524            }
525        }
526
527        osg::notify(osg::NOTICE)<<"done LoadAndCompileOperation "<<_filename<<std::endl;
528    }
529
530    virtual bool compileCompleted(osgUtil::IncrementalCompileOperation::CompileSet* compileSet)
531    {
532        OSG_NOTICE<<"compileCompleted"<<std::endl;
533        _modelReadyToMerge = true;
534        return true;
535    }
536
537    std::string                                         _filename;
538    std::string                                         _outputFilename;
539    osg::ref_ptr<osg::Node>                             _loadedModel;
540    bool                                                _modelReadyToMerge;
541    osg::ref_ptr<SceneGraphProcessor>                   _sceneGraphProcessor;
542    osg::ref_ptr<osgUtil::IncrementalCompileOperation>  _incrementalCompileOperation;
543};
544
545class TexturePoolHandler : public osgGA::GUIEventHandler
546{
547public:
548    virtual bool handle(const osgGA::GUIEventAdapter& ea,osgGA::GUIActionAdapter& aa)
549    {
550        if (ea.getEventType() == osgGA::GUIEventAdapter::KEYUP)
551        {
552            if (ea.getKey()=='r')
553            {
554                osg::Texture::getTextureObjectManager(0)->reportStats();
555                osg::GLBufferObjectManager::getGLBufferObjectManager(0)->reportStats();
556            }
557        }
558        return false;
559    }
560};
561
562
563int main(int argc, char** argv)
564{
565    osg::ArgumentParser arguments(&argc, argv);
566
567    // construct the viewer.
568    osgViewer::Viewer viewer(arguments);
569
570    // set up camera manipulators
571    {
572        osg::ref_ptr<osgGA::KeySwitchMatrixManipulator> keyswitchManipulator = new osgGA::KeySwitchMatrixManipulator;
573
574        keyswitchManipulator->addMatrixManipulator( '1', "Trackball", new osgGA::TrackballManipulator() );
575        keyswitchManipulator->addMatrixManipulator( '2', "Flight", new osgGA::FlightManipulator() );
576        keyswitchManipulator->addMatrixManipulator( '3', "Drive", new osgGA::DriveManipulator() );
577        keyswitchManipulator->addMatrixManipulator( '4', "Terrain", new osgGA::TerrainManipulator() );
578
579        std::string pathfile;
580        char keyForAnimationPath = '8';
581        while (arguments.read("-p",pathfile))
582        {
583            osgGA::AnimationPathManipulator* apm = new osgGA::AnimationPathManipulator(pathfile);
584            if (apm || !apm->valid())
585            {
586                unsigned int num = keyswitchManipulator->getNumMatrixManipulators();
587                keyswitchManipulator->addMatrixManipulator( keyForAnimationPath, "Path", apm );
588                keyswitchManipulator->selectMatrixManipulator(num);
589                ++keyForAnimationPath;
590            }
591        }
592
593        viewer.setCameraManipulator( keyswitchManipulator.get() );
594    }
595
596    // set up event handlers
597    {
598        viewer.addEventHandler( new osgViewer::StatsHandler());
599        viewer.addEventHandler( new osgViewer::WindowSizeHandler() );
600        viewer.addEventHandler( new osgGA::StateSetManipulator(viewer.getCamera()->getOrCreateStateSet()) );
601        viewer.addEventHandler( new TexturePoolHandler() );
602    }
603
604    /////////////////////////////////////////////////////////////////////////////////
605    //
606    // IncrementalCompileOperation settings
607    //
608    osg::ref_ptr<osgUtil::IncrementalCompileOperation> incrementalCompile = new osgUtil::IncrementalCompileOperation;
609    viewer.setIncrementalCompileOperation(incrementalCompile.get());
610
611    if (arguments.read("--force") || arguments.read("-f"))
612    {
613        incrementalCompile->assignForceTextureDownloadGeometry();
614    }
615
616    if (arguments.read("-a"))
617    {
618        incrementalCompile->setMinimumTimeAvailableForGLCompileAndDeletePerFrame(1);
619        incrementalCompile->setConservativeTimeRatio(1);
620        incrementalCompile->setMaximumNumOfObjectsToCompilePerFrame(100);
621    }
622    else if (arguments.read("-c"))
623    {
624        incrementalCompile->setMinimumTimeAvailableForGLCompileAndDeletePerFrame(0.0001);
625        incrementalCompile->setConservativeTimeRatio(0.01);
626        incrementalCompile->setMaximumNumOfObjectsToCompilePerFrame(1);
627    }
628
629    /////////////////////////////////////////////////////////////////////////////////
630    //
631    // SceneGraph processing setup
632    //
633    osg::ref_ptr<SceneGraphProcessor> sceneGraphProcessor = new SceneGraphProcessor(arguments);
634
635    /////////////////////////////////////////////////////////////////////////////////
636    //
637    // Database settings
638    //
639    double timeBetweenMerges = 2.0;
640    while(arguments.read("--interval",timeBetweenMerges)) {}
641
642    std::string outputPostfix;
643    while (arguments.read("-o",outputPostfix)) { OSG_NOTICE<<"Set ouputPostfix to "<<outputPostfix<<std::endl; }
644
645
646    typedef std::vector< std::string > FileNames;
647    FileNames fileNames;
648    for(int pos=1;pos<arguments.argc();++pos)
649    {
650        if (!arguments.isOption(pos))
651        {
652            fileNames.push_back(arguments[pos]);
653        }
654    }
655
656    if (fileNames.empty())
657    {
658        OSG_NOTICE<<"No files loaded, please specify files on commandline."<<std::endl;
659        return 1;
660    }
661
662    // load the models using a paging thread and use the incremental compile operation to
663    // manage the compilation of GL objects without breaking frame.
664
665    unsigned int modelIndex = 0;
666
667    osg::ref_ptr<osg::OperationThread> databasePagingThread;
668    osg::ref_ptr<DatabasePagingOperation> databasePagingOperation;
669
670    databasePagingThread = new osg::OperationThread;
671    databasePagingThread->startThread();
672
673    std::string filename = fileNames[modelIndex++];
674    std::string outputFilename = outputPostfix.empty() ? std::string() : osgDB::getStrippedName(filename)+outputPostfix;
675
676    databasePagingOperation = new DatabasePagingOperation(
677        filename,
678        outputFilename,
679        sceneGraphProcessor.get(),
680        incrementalCompile.get());
681
682    databasePagingThread->add(databasePagingOperation.get());
683
684    osg::ref_ptr<osg::Group> group = new osg::Group;
685    viewer.setSceneData(group.get());
686
687    viewer.realize();
688
689    double timeOfLastMerge = viewer.getFrameStamp()->getReferenceTime();
690
691    while(!viewer.done())
692    {
693        viewer.frame();
694
695        double currentTime = viewer.getFrameStamp()->getReferenceTime();
696
697        if (!databasePagingOperation &&
698            modelIndex<fileNames.size() &&
699            (currentTime-timeOfLastMerge)>timeBetweenMerges)
700        {
701            std::string filename = fileNames[modelIndex++];
702            std::string outputFilename = outputPostfix.empty() ? std::string() : osgDB::getStrippedName(filename)+outputPostfix;
703
704            databasePagingOperation = new DatabasePagingOperation(
705                filename,
706                outputFilename,
707                sceneGraphProcessor.get(),
708                incrementalCompile.get());
709
710            databasePagingThread->add(databasePagingOperation.get());
711        }
712
713        if (databasePagingOperation.get() && databasePagingOperation->_modelReadyToMerge)
714        {
715            timeOfLastMerge = currentTime;
716
717            group->removeChildren(0,group->getNumChildren());
718
719            group->addChild(databasePagingOperation->_loadedModel.get());
720
721            viewer.home();
722
723            // we no longer need the paging operation as it's done it's job.
724            databasePagingOperation = 0;
725
726            viewer.home();
727        }
728    }
729
730    return 0;
731}
Note: See TracBrowser for help on using the browser.