source: osgVisual/include/distortion/visual_distortion.h @ 88

Last change on this file since 88 was 88, checked in by Torben Dannhauer, 14 years ago

Moved memory leak detection from source file to headerfile. Its still in the class but at least not in the source file.

The leak detection works, but the false positives are not stopped.
Use Linux/Valgrind? to make your final leak detection beyond the easy first approach in MSVC

File size: 13.5 KB
Line 
1#pragma once
2/* -*-c++-*- osgVisual - Copyright (C) 2009-2010 Torben Dannhauer
3 *
4 * This library is based on OpenSceneGraph, open source and may be redistributed and/or modified under
5 * the terms of the OpenSceneGraph Public License (OSGPL) version 0.0 or
6 * (at your option) any later version.  The full license is in LICENSE file
7 * included with this distribution, and on the openscenegraph.org website.
8 *
9 * osgVisual requires for some proprietary modules a license from the correspondig manufacturer.
10 * You have to aquire licenses for all used proprietary modules.
11 *
12 * This library is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 * OpenSceneGraph Public License for more details.
16*/
17
18#include <osg/NodeCallback>
19#include <osg/Node>
20#include <osg/Geode>
21#include <osg/Geometry>
22#include <osg/Texture2D>
23#include <osg/TextureRectangle>
24#include <osg/Notify>
25#include <osg/Referenced>
26
27#include <osgViewer/Viewer>
28
29#include <osgDB/ReadFile>
30#include <osgDB/FileUtils>
31
32#include <osgGA/GUIEventHandler>
33#include <osgGA/GUIActionAdapter>
34
35#include <string>
36#include <iostream>
37#include <fstream>
38
39
40namespace osgVisual
41{
42
43
44//class CameraConfigParser;
45
46/**
47 * \brief This class distorts and blends the rendered image for projection in curved screens and multi channel setups.
48 *
49 * @todo Distortion algorithm seems to be erronous, small artefact lines are visible.
50 *
51 * @author Torben Dannhauer
52 * @date  Jul 2009
53 */ 
54class visual_distortion : public osg::Node
55{
56        #include <leakDetection.h>
57public:
58        /**
59         * \brief Constructor
60         *
61         */ 
62        visual_distortion(osgViewer::Viewer* viewer_, osg::ArgumentParser& arguments_);
63
64        /**
65         * \brief Destructor
66         *
67         */ 
68        virtual ~visual_distortion(void);
69
70        /**
71         * \brief This function parses the arguments for distortion relevant parameters.
72         *
73         * @return : True if parsing was successful.
74         */ 
75        bool processCommandlineparameters();
76
77        /**
78         * \brief This function initializes the distortion node and creates the distortion camera and scene graph.
79         *
80         * @param subgraph : Undistorted scene graph.
81         * @param clearColor : Clear color for distortion.
82         * @return : Group node which contains the distortion and the undistorted scene graph.
83         */ 
84        osg::Group* initialize(osg::Group* subgraph, const osg::Vec4& clearColor );
85
86        /**
87         * \brief This function shuts the distortion module down.
88         *
89         */ 
90        void shutdown();
91
92        /**
93         * \brief This function enabels or disables the distortion
94         */ 
95        void toggleDistortion();
96
97        /**
98         * \brief This functions returns a pointer to the scene camera, which renders the undistorted scene (PRE_RENDER).
99         *
100         * @return Pointer to the scene camera.
101         */ 
102        osg::Camera* getSceneCamera() {return sceneCamera;};
103
104        /**
105         * \brief This function returns the distortedSceneGraph if the distortion module is initialized.
106         *
107         * @return NULL if not Initialized, Otherwith the distorted sceneGraph.
108         */ 
109        osg::Group* getDistortedSceneGraph() { if(initialized) return distortedGraph; else return NULL;};
110
111        /**
112         * \brief The function returns the frustum values which are parsed by the nested cameraConfigParser class.
113         *
114         * @return : Vector of double values which represent the frustum dataset. The order is the standart glu order.
115         */ 
116        std::vector<double> getFrustumDataset() {return parser->getFrustumDataset();};
117                       
118        /**
119         * \brief This function returns the retation values for the rendering camera for XYZ axis in degree.
120         *
121         * @return : Vector of double values which represent the rotation values for XYZ axis in degree.
122         */ 
123        std::vector<double> getRotationDataset() {return parser->getRotationDataset();};
124
125        /**
126         * \brief This function returns the translation values for the rendering camera along the XYZ axis in meter.
127         *
128         * @return : Vector of double values which represent the translation values for XYZ axis in meter.
129         */ 
130        std::vector<double> getTranslationDataset() {return parser->getTranslationDataset();};
131
132private:
133        /**
134         * \brief Callback class for update callback.
135         *
136         * This nested class is used for updating the distortion node every frame by installing this class as updateCallback for the distortion node.
137         * @author Torben Dannhauer
138         * @date  Jul 2009
139         */ 
140        class distortionUpdateCallback : public osg::NodeCallback
141        {
142        public: 
143                /**
144                 * \brief Constructor, for setting the member variables.
145                 *
146                 * @param viewer_ : Pointer to the viewer.
147                 * @param sceneCamera_ : Pointer to the scene camera.
148                 */ 
149                distortionUpdateCallback(osgViewer::Viewer* viewer_, osg::Camera* sceneCamera_)
150                        : viewer(viewer_), sceneCamera(sceneCamera_) {};
151
152                /**
153                 * \brief This function is executed as callback during update traversal.
154                 *
155                 */ 
156                virtual void operator()(osg::Node* node, osg::NodeVisitor* nv);
157        private:
158                /**
159                 * Referenced Pointer to the applications viewer.
160                 */ 
161                osg::ref_ptr<osgViewer::Viewer> viewer;
162
163                /**
164                 * Referenced Pointer to the scene camera.
165                 */ 
166                osg::ref_ptr<osg::Camera> sceneCamera;
167        };
168
169        /**
170         * \brief This nested class is a keyboard event adapter which allows distortion toggle. It never blocks the key event, therefore multiple events on a single key are possible.
171         *
172         * @author Torben Dannhauer
173         * @date  Jul 2009
174         */ 
175        class ToggleDistortionKBEventHandler : public osgGA::GUIEventHandler
176        {
177        public:
178                /**
179                 * \brief Constructor
180                 *
181                 * @param distortion_ : Pointer to the distortion class.
182                 * @param viewer_ : Reference to the applications viewer.
183                 */ 
184                ToggleDistortionKBEventHandler(visual_distortion* distortion_): distortion(distortion_) {}
185
186                /**
187                 * \brief This function is executed if an keyboard event appears
188                 *
189                 * @param ea : GUI event adapter.
190                 * @param : GUI action adapter.
191                 * @return : Returns always false to pass the event to other event adapter if installed.
192                 */   
193                virtual bool handle(const osgGA::GUIEventAdapter& ea,osgGA::GUIActionAdapter&)
194                {
195                        if ( ea.getEventType() == osgGA::GUIEventAdapter::KEYDOWN &&  ea.getKey() == 'd' )
196                        {
197                                distortion->toggleDistortion();
198                                return false;
199                        }
200                        else
201                                return false;   // return false means: hand over the event to the next Eventhandler.  True means: absorb the event.
202                }
203
204        private:
205                /**
206                 * Pointer to he distortion class. INside this EventHandler a Referenced Pointer ist _NOT_ used,
207                 * because a circulare reference (distortion->kBEventHandler, kbEventHandler->distortion) would block both pointer to unref.
208                 */ 
209                visual_distortion* distortion;
210        };
211
212        /**
213         * \brief This nested class reads the Projection Designer's project file and extracts the frustum, translation and rotation values
214         *
215         * @author Torben Dannhauer
216         * @date  Aug 2009
217         */ 
218        class CameraConfigParser : public osg::Referenced
219        {
220        public:
221                CameraConfigParser(void)
222                {
223                        configParsed = false;
224                        frustumValues.clear();
225                        rotationValues.clear();
226                        rotationValues.resize(3,0);
227                        translationValues.clear();
228                        translationValues.resize(3,0);
229                }
230
231                virtual ~CameraConfigParser(void) {};
232
233                bool parseConfigFile(const char * filename)
234                {
235                  if (! osgDB::fileExists(filename) )
236                  {
237                          OSG_NOTIFY( osg::FATAL ) << "ERROR: File '" << filename << "' does not exist." << std::endl;
238                          return false;
239                  }
240
241                  frustumValues.clear();
242                  rotationValues.clear();
243                  rotationValues.resize(3,0);
244                  translationValues.clear();
245                  translationValues.resize(3,0);
246
247                  std::string line;
248                  std::ifstream configFile (filename);
249
250                  if (configFile.is_open())
251                  {
252                        while (! configFile.eof() )
253                        {
254                          getline (configFile,line);
255                          //cout << line << endl;
256
257                          // Auf Frustum untersuchen
258                          if( line.find("Frustum") != std::string::npos )
259                          {
260                                  extractFrustum(line);
261                          }
262
263                          // Auf Rotation untersuchen
264                          if( line.find("Rotate") != std::string::npos )
265                          {
266                                 extractRotation(line);
267                          }
268
269                          // Auf Translation untersuchens
270                          if( line.find("Translate") != std::string::npos )
271                          {
272                                 extractTranslation(line);
273                          }
274
275                        }
276                        configFile.close();
277                        configParsed = true;
278                        return true;
279                  }
280                  else 
281                  {
282                          OSG_NOTIFY( osg::FATAL ) << "Unable to open file:" << filename << std::endl;
283                          frustumValues.clear();
284                          configParsed = false;
285                          return false;
286                  }
287                }
288
289                bool extractFrustum(std::string data_)
290                {
291                        data_.replace(0,16,"");         // Delete leading spaces and "Frustum"
292                        data_.replace(data_.length()-1,1,"");   // Delete trailing ";"
293                        for( int i=0; i<6; i++)
294                        {
295                                size_t pos = data_.find(" ");    // Position of first value in string
296                                if( pos == -1) pos = data_.length();
297                                frustumValues.push_back( atof( data_.substr(0, pos).data() ) );
298                                data_.replace(0,pos+1,"");
299                        }
300                        return true;
301                }
302
303                bool extractRotation(std::string data_)
304                {
305                        data_.replace(0,15,"");         // Delete leading spaces and "Rotate"
306                        data_.replace(data_.length()-1,1,"");   // Delete trailing ";"
307
308                        size_t valuePos = data_.find(" ");    // First Value is RotationValue
309                        std::string axis = data_.substr( valuePos+1);
310                        switch(axis.find("1"))
311                        {
312                                case 0: rotationValues[0] = atof( data_.substr(0, valuePos).data() ); // X-Axis
313                                        break;
314                                case 2: rotationValues[1] = atof( data_.substr(0, valuePos).data() ); // Y-Axis
315                                        break;
316                                case 4: rotationValues[2] = atof( data_.substr(0, valuePos).data() ); // Z-Axis
317                                        break;
318                        };
319                        return true;
320                }
321
322                bool extractTranslation(std::string data_)
323                {
324                        data_.replace(0,18,"");         // Delete leading spaces and "Translate"
325                        data_.replace(data_.length()-1,1,"");   // Delete trailing ";"
326                        for( unsigned int i=0;i<translationValues.size(); i++)
327                        {
328                                size_t valuePos = data_.find(" ");
329                                std::string value = data_.substr(0, valuePos);
330                                data_.replace(0,valuePos+1,"");
331                                translationValues[i] = atof( value.data() );
332                        }
333                        return true;
334                }
335
336                std::vector<double> getFrustumDataset() {return(frustumValues);}
337                       
338                std::vector<double> getRotationDataset() {return(rotationValues);}
339
340                std::vector<double> getTranslationDataset() {return(translationValues);}
341
342                bool isConfigParsed() {return configParsed;};
343        private:
344                bool configParsed;
345                std::vector<double> frustumValues;
346                std::vector<double> rotationValues;
347                std::vector<double> translationValues;
348        };
349
350
351
352        /**
353         * Updatecallback as member variable of this class.
354         */ 
355        osg::ref_ptr<distortionUpdateCallback> updateCallback;
356
357        /**
358         * Keyboard Eventhandler for distortion toggle.
359         */ 
360        //osg::ref_ptr<ToggleDistortionKBEventHandler> kBEventHandler;
361        ToggleDistortionKBEventHandler* kBEventHandler;
362
363        /**
364         * \brief This functions creates the distortion environment.
365         *
366         * @param subgraph : Undistorted scene graph to distort.
367         * @param clearColor : OpenGL clear color to use for the distortion.
368         * @return : Group node which contains the distortion and the undistorted scene graph.
369         */ 
370        osg::Group* createPreRenderSubGraph(osg::Group* subgraph, const osg::Vec4& clearColor );
371
372        /**
373         * \brief This function loads a shader source file
374         *
375         * @param shader : Shader to load source in
376         * @param fileName : Filename of shader source file.
377         * @return : Returns true if successful.
378         */ 
379        bool loadShaderSource( osg::Shader* shader, const std::string& fileName );
380
381        /**
382         * \brief This function loads a shader Texture file
383         *
384         * @param fileName : Texture file to load.
385         * @return : Returns the loaded Texture.
386         */ 
387        osg::Texture* loadTexture( const std::string& fileName );
388       
389        /**
390         * Referenced Pointer to the loaded distortion Map
391         */ 
392        osg::ref_ptr<osg::Texture> distortMapTexture;
393
394        /**
395         * Referenced Pointer to the loaded blend map
396         */ 
397        osg::ref_ptr<osg::Texture> blendMapTexture;
398
399
400        /**
401         * Flag which indicates the initialization status
402         */ 
403        bool initialized;
404
405        /**
406         * Flag that indicates if distortion is actually enabled. This is imported for the toggleDistortion() function.
407         */ 
408        bool distortionEnabled;
409
410        /**
411         * Reference pointer to the distorted scene graph.
412         */ 
413        osg::ref_ptr<osg::Group> distortedGraph;
414
415        /**
416         * Reference pointer to the undistorted scene graph.
417         */ 
418        osg::ref_ptr<osg::Group> cleanGraph;
419
420        /**
421         * Reference pointer to the scen camera (PRE_RENDER)
422         */ 
423        osg::ref_ptr<osg::Camera> sceneCamera;
424
425        /**
426         * Referenced pointer to the main applications viewer
427         */ 
428        osg::ref_ptr<osgViewer::Viewer> viewer;
429
430        /**
431         * Parser object for parsing the camera configuration file which controlls frustum and camera PAT
432         */ 
433        osg::ref_ptr<CameraConfigParser> parser;
434
435        /**
436         * Texture width for render to texture (RTT).
437         */ 
438        unsigned tex_width;
439
440        /**
441         * Texture height for using render to texture (RTT).
442         */ 
443    unsigned tex_height;
444
445        /**
446         * Indicates of texture rectangle should be used.
447         */ 
448        bool useTextureRectangle;
449
450        /**
451         * Indicates if shader distortion should be used.
452         */ 
453        bool useShaderDistortion;
454
455        /**
456         * Indicates if high definition rendering shold be used.
457         */ 
458        bool useHDR;
459
460        /**
461         * Filename of the distorion map.
462         */ 
463        std::string distortMapFileName;
464
465        /**
466         * Filename of the blend map.
467         */ 
468        std::string blendMapFileName;
469
470        /**
471         * Target implementation which should be used to distort.
472         */ 
473        osg::Camera::RenderTargetImplementation renderImplementation;
474
475        /**
476         * Reference to the global ArgumentParser.
477         */ 
478        osg::ArgumentParser& arguments;
479};
480
481}       // END NAMESPACE
Note: See TracBrowser for help on using the repository browser.