root/OpenSceneGraph/trunk/examples/osgmanipulator/osgmanipulator.cpp @ 10436

Revision 10436, 12.0 kB (checked in by robert, 5 years ago)

Completed refactor of osgManipulator, key changes are:

Selection is now just a typedef of osg::MatrixTransform?, and is deprecated

CommandManager? is shell class that just sets values directly on Dragger, and is deprecated

Dragger now has list of DraggerCallback? that takes over the roll of tracking changes to the Dragger, and
allows users to track the dragger in any way they wish.

Dragger now has a convinience method making MatrixTransforms? track a dragger.

Selection and CommandManager? are no longer required for use of osgManipulator and are kept around for backwards compatibility.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
Line 
1/* OpenSceneGraph example, osgmanipulator.
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#include <osgDB/ReadFile>
20#include <osgUtil/Optimizer>
21#include <osgViewer/Viewer>
22#include <osg/CoordinateSystemNode>
23#include <osgText/Text>
24
25#include <osgManipulator/CommandManager>
26#include <osgManipulator/TabBoxDragger>
27#include <osgManipulator/TabPlaneDragger>
28#include <osgManipulator/TabPlaneTrackballDragger>
29#include <osgManipulator/TrackballDragger>
30#include <osgManipulator/Translate1DDragger>
31#include <osgManipulator/Translate2DDragger>
32#include <osgManipulator/TranslateAxisDragger>
33
34#include <osg/ShapeDrawable>
35#include <osg/MatrixTransform>
36#include <osg/Geometry>
37#include <osg/Material>
38
39#include <iostream>
40
41// #define USE_COMMAND_MANAGER
42
43osgManipulator::Dragger* createDragger(const std::string& name)
44{
45    osgManipulator::Dragger* dragger = 0;
46    if ("TabPlaneDragger" == name)
47    {
48        osgManipulator::TabPlaneDragger* d = new osgManipulator::TabPlaneDragger();
49        d->setupDefaultGeometry();
50        dragger = d;
51    }
52    else if ("TabPlaneTrackballDragger" == name)
53    {
54        osgManipulator::TabPlaneTrackballDragger* d = new osgManipulator::TabPlaneTrackballDragger();
55        d->setupDefaultGeometry();
56        dragger = d;
57    }
58    else if ("TrackballDragger" == name)
59    {
60        osgManipulator::TrackballDragger* d = new osgManipulator::TrackballDragger();
61        d->setupDefaultGeometry();
62        dragger = d;
63    }
64    else if ("Translate1DDragger" == name)
65    {
66        osgManipulator::Translate1DDragger* d = new osgManipulator::Translate1DDragger();
67        d->setupDefaultGeometry();
68        dragger = d;
69    }
70    else if ("Translate2DDragger" == name)
71    {
72        osgManipulator::Translate2DDragger* d = new osgManipulator::Translate2DDragger();
73        d->setupDefaultGeometry();
74        dragger = d;
75    }
76    else if ("TranslateAxisDragger" == name)
77    {
78        osgManipulator::TranslateAxisDragger* d = new osgManipulator::TranslateAxisDragger();
79        d->setupDefaultGeometry();
80        dragger = d;
81    }
82    else
83    {
84        osgManipulator::TabBoxDragger* d = new osgManipulator::TabBoxDragger();
85        d->setupDefaultGeometry();
86        dragger = d;
87    }
88
89   
90 
91    return dragger;
92}
93
94
95osg::Node* addDraggerToScene(osg::Node* scene, osgManipulator::CommandManager* cmdMgr, const std::string& name)
96{
97    scene->getOrCreateStateSet()->setMode(GL_NORMALIZE, osg::StateAttribute::ON);
98
99    osgManipulator::Selection* selection = new osgManipulator::Selection;
100    selection->addChild(scene);
101
102    osgManipulator::Dragger* dragger = createDragger(name);
103
104    dragger->setHandleEvents(true);
105
106    osg::Group* root = new osg::Group;
107    root->addChild(dragger);
108    root->addChild(selection);
109
110    float scale = scene->getBound().radius() * 1.6;
111    dragger->setMatrix(osg::Matrix::scale(scale, scale, scale) *
112                       osg::Matrix::translate(scene->getBound().center()));
113
114#ifdef USE_COMMAND_MANAGER
115    cmdMgr->connect(*dragger, *selection);
116#else
117    dragger->addTransformUpdating(selection);
118#endif
119    return root;
120}
121
122osg::Node* createDemoScene(osgManipulator::CommandManager* cmdMgr) {
123 
124    osg::Group* root = new osg::Group;
125
126    osg::ref_ptr<osg::Geode> geode_1 = new osg::Geode;
127    osg::ref_ptr<osg::MatrixTransform> transform_1 = new osg::MatrixTransform;
128
129    osg::ref_ptr<osg::Geode> geode_2 = new osg::Geode;
130    osg::ref_ptr<osg::MatrixTransform> transform_2 = new osg::MatrixTransform;
131
132    osg::ref_ptr<osg::Geode> geode_3 = new osg::Geode;
133    osg::ref_ptr<osg::MatrixTransform> transform_3 = new osg::MatrixTransform;
134
135    osg::ref_ptr<osg::Geode> geode_4 = new osg::Geode;
136    osg::ref_ptr<osg::MatrixTransform> transform_4 = new osg::MatrixTransform;
137
138    osg::ref_ptr<osg::Geode> geode_5 = new osg::Geode;
139    osg::ref_ptr<osg::MatrixTransform> transform_5 = new osg::MatrixTransform;
140
141    osg::ref_ptr<osg::Geode> geode_6 = new osg::Geode;
142    osg::ref_ptr<osg::MatrixTransform> transform_6 = new osg::MatrixTransform;
143
144    osg::ref_ptr<osg::Geode> geode_7 = new osg::Geode;
145    osg::ref_ptr<osg::MatrixTransform> transform_7 = new osg::MatrixTransform;
146
147 
148
149
150
151    const float radius = 0.8f;
152    const float height = 1.0f;
153    osg::ref_ptr<osg::TessellationHints> hints = new osg::TessellationHints;
154    hints->setDetailRatio(2.0f);
155    osg::ref_ptr<osg::ShapeDrawable> shape;
156
157    shape = new osg::ShapeDrawable(new osg::Box(osg::Vec3(0.0f, 0.0f, -2.0f), 10, 10.0f, 0.1f), hints.get());
158    shape->setColor(osg::Vec4(0.5f, 0.5f, 0.7f, 1.0f));
159    geode_1->addDrawable(shape.get());
160
161    shape = new osg::ShapeDrawable(new osg::Cylinder(osg::Vec3(0.0f, 0.0f, 0.0f), radius * 2,radius), hints.get());
162    shape->setColor(osg::Vec4(0.8f, 0.8f, 0.8f, 1.0f));
163    geode_2->addDrawable(shape.get());
164
165    shape = new osg::ShapeDrawable(new osg::Cylinder(osg::Vec3(-3.0f, 0.0f, 0.0f), radius,radius), hints.get());
166    shape->setColor(osg::Vec4(0.6f, 0.8f, 0.8f, 1.0f));
167    geode_3->addDrawable(shape.get());
168
169    shape = new osg::ShapeDrawable(new osg::Cone(osg::Vec3(3.0f, 0.0f, 0.0f), 2 * radius,radius), hints.get());
170    shape->setColor(osg::Vec4(0.4f, 0.9f, 0.3f, 1.0f));
171    geode_4->addDrawable(shape.get());
172
173    shape = new osg::ShapeDrawable(new osg::Cone(osg::Vec3(0.0f, -3.0f, 0.0f), radius, height), hints.get());
174    shape->setColor(osg::Vec4(0.2f, 0.5f, 0.7f, 1.0f));
175    geode_5->addDrawable(shape.get());
176
177    shape = new osg::ShapeDrawable(new osg::Cylinder(osg::Vec3(0.0f, 3.0f, 0.0f), radius, height), hints.get());
178    shape->setColor(osg::Vec4(1.0f, 0.3f, 0.3f, 1.0f));
179    geode_6->addDrawable(shape.get());
180
181    shape = new osg::ShapeDrawable(new osg::Cone(osg::Vec3(0.0f, 0.0f, 3.0f), 2.0f, 2.0f), hints.get());
182    shape->setColor(osg::Vec4(0.8f, 0.8f, 0.4f, 1.0f));
183    geode_7->addDrawable(shape.get());
184
185
186
187
188
189
190    // material
191    osg::ref_ptr<osg::Material> matirial = new osg::Material;
192    matirial->setColorMode(osg::Material::DIFFUSE);
193    matirial->setAmbient(osg::Material::FRONT_AND_BACK, osg::Vec4(0, 0, 0, 1));
194    matirial->setSpecular(osg::Material::FRONT_AND_BACK, osg::Vec4(1, 1, 1, 1));
195    matirial->setShininess(osg::Material::FRONT_AND_BACK, 64.0f);
196    root->getOrCreateStateSet()->setAttributeAndModes(matirial.get(), osg::StateAttribute::ON);
197
198      transform_1.get()->addChild(addDraggerToScene(geode_1.get(),cmdMgr,"TabBoxDragger"));
199    transform_2.get()->addChild(addDraggerToScene(geode_2.get(),cmdMgr,"TabPlaneDragger"));
200    transform_3.get()->addChild(addDraggerToScene(geode_3.get(),cmdMgr,"TabPlaneTrackballDragger"));
201    transform_4.get()->addChild(addDraggerToScene(geode_4.get(),cmdMgr,"TrackballDragger"));
202    transform_5.get()->addChild(addDraggerToScene(geode_5.get(),cmdMgr,"Translate1DDragger"));
203    transform_6.get()->addChild(addDraggerToScene(geode_6.get(),cmdMgr,"Translate2DDragger"));
204    transform_7.get()->addChild(addDraggerToScene(geode_7.get(),cmdMgr,"TranslateAxisDragger"));
205
206    root->addChild(transform_1.get());
207    root->addChild(transform_2.get());
208    root->addChild(transform_3.get());
209    root->addChild(transform_4.get());
210    root->addChild(transform_5.get());
211    root->addChild(transform_6.get());
212    root->addChild(transform_7.get());
213
214 
215 
216    return root;
217}
218//
219int main( int argc, char **argv )
220{
221
222    // use an ArgumentParser object to manage the program arguments.
223    osg::ArgumentParser arguments(&argc,argv);
224   
225    // set up the usage document, in case we need to print out how to use this program.
226    arguments.getApplicationUsage()->setApplicationName(arguments.getApplicationName());
227    arguments.getApplicationUsage()->setCommandLineUsage(arguments.getApplicationName()+" [options] filename ...");
228    arguments.getApplicationUsage()->addCommandLineOption("--image <filename>","Load an image and render it on a quad");
229    arguments.getApplicationUsage()->addCommandLineOption("--dem <filename>","Load an image/DEM and render it on a HeightField");
230    arguments.getApplicationUsage()->addCommandLineOption("-h or --help","Display command line parameters");
231    arguments.getApplicationUsage()->addCommandLineOption("--help-env","Display environmental variables available");
232    arguments.getApplicationUsage()->addCommandLineOption("--help-keys","Display keyboard & mouse bindings available");
233    arguments.getApplicationUsage()->addCommandLineOption("--help-all","Display all command line, env vars and keyboard & mouse bindings.");
234
235    arguments.getApplicationUsage()->addCommandLineOption("--dragger <draggername>","Use the specified dragger for manipulation [TabPlaneDragger,TabPlaneTrackballDragger,TrackballDragger,Translate1DDragger,Translate2DDragger,TranslateAxisDragger,TabBoxDragger]");
236   
237
238    // construct the viewer.
239    osgViewer::Viewer viewer;
240
241    // get details on keyboard and mouse bindings used by the viewer.
242    viewer.getUsage(*arguments.getApplicationUsage());
243
244    // if user request help write it out to cout.
245    bool helpAll = arguments.read("--help-all");
246    unsigned int helpType = ((helpAll || arguments.read("-h") || arguments.read("--help"))? osg::ApplicationUsage::COMMAND_LINE_OPTION : 0 ) |
247                            ((helpAll ||  arguments.read("--help-env"))? osg::ApplicationUsage::ENVIRONMENTAL_VARIABLE : 0 ) |
248                            ((helpAll ||  arguments.read("--help-keys"))? osg::ApplicationUsage::KEYBOARD_MOUSE_BINDING : 0 );
249    if (helpType)
250    {
251        arguments.getApplicationUsage()->write(std::cout, helpType);
252        return 1;
253    }
254
255    // report any errors if they have occurred when parsing the program arguments.
256    if (arguments.errors())
257    {
258        arguments.writeErrorMessages(std::cout);
259        return 1;
260    }
261
262    std::string dragger_name = "TabBoxDragger";
263    arguments.read("--dragger", dragger_name);
264
265    osg::Timer_t start_tick = osg::Timer::instance()->tick();
266
267    // read the scene from the list of file specified command line args.
268    osg::ref_ptr<osg::Node> loadedModel = osgDB::readNodeFiles(arguments);
269
270    // create a command manager
271    osg::ref_ptr<osgManipulator::CommandManager> cmdMgr;
272
273
274#ifdef USE_COMMAND_MANAGER
275    cmdMgr = new osgManipulator::CommandManager;
276#endif
277
278    // if no model has been successfully loaded report failure.
279    bool tragger2Scene(true);
280    if (!loadedModel)
281    {
282        //std::cout << arguments.getApplicationName() <<": No data loaded" << std::endl;
283        //return 1;
284        loadedModel = createDemoScene(cmdMgr.get());
285        tragger2Scene=false;
286    }
287
288    // any option left unread are converted into errors to write out later.
289    arguments.reportRemainingOptionsAsUnrecognized();
290
291    // report any errors if they have occurred when parsing the program arguments.
292    if (arguments.errors())
293    {
294        arguments.writeErrorMessages(std::cout);
295    }
296
297    osg::Timer_t end_tick = osg::Timer::instance()->tick();
298
299    std::cout << "Time to load = "<<osg::Timer::instance()->delta_s(start_tick,end_tick)<<std::endl;
300
301
302    // optimize the scene graph, remove redundant nodes and state etc.
303    osgUtil::Optimizer optimizer;
304    optimizer.optimize(loadedModel.get());
305
306   
307    // pass the loaded scene graph to the viewer.
308    if ( tragger2Scene ) {
309        viewer.setSceneData(addDraggerToScene(loadedModel.get(), cmdMgr.get(), dragger_name));
310    } else {
311        viewer.setSceneData(loadedModel.get());
312    }
313
314
315    return viewer.run();
316}
Note: See TracBrowser for help on using the browser.