source: experimental/distortionNG/DistortionSetupStrategyProjectSyntropy.cpp @ 410

Last change on this file since 410 was 410, checked in by Torben Dannhauer, 12 years ago

New Distortion setup strategy added: distortionNG can now handle configuration files of "Projection Designer"

File size: 13.0 KB
Line 
1/* osgVisual test. distortionNG, experimental.
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 <osg/Vec3d>
20#include <osg/ImageUtils>
21#include <osgDB/FileUtils>
22#include <osgDB/ReadFile>
23#include <osgDB/fstream>
24
25#include "DistortionSetupStrategyProjectSyntropy.h"
26
27DistortionSetupStrategyProjectSyntropy::DistortionSetupStrategyProjectSyntropy()
28{
29        _blendmapFilename = "";
30        _frustumFilename = "";
31        _distortionFilename = "";
32
33        _distortionInitialized=false;
34}
35
36DistortionSetupStrategyProjectSyntropy::~DistortionSetupStrategyProjectSyntropy()
37{
38
39}
40
41void DistortionSetupStrategyProjectSyntropy::setDistortionInputFiles(std::string distortionFile, std::string blendmapFile, std::string frustumFile)
42{
43        _blendmapFilename = blendmapFile;
44        _frustumFilename = frustumFile;
45        _distortionFilename = distortionFile;
46}
47
48int DistortionSetupStrategyProjectSyntropy::readFrustumFromCSVFile(std::string filePath, int numValues, float* frustumValues)
49{
50        int numSeparator=0;
51        std::string line, valueString;
52        char separator=';';
53        size_t valueStart, valueEnd;
54
55        osgDB::ifstream inputFile (const_cast<char*>(filePath.c_str()));
56
57        for (int i=0;i<numValues; i++) frustumValues[i]=0.0;
58
59        if (inputFile.is_open())
60        {
61                inputFile.clear();
62                inputFile.seekg (0, std::ios::beg);
63
64                while (!inputFile.eof())
65                {
66                        getline (inputFile,line);
67
68                        if((line.size()>0) && (line.find('x')==std::string::npos))
69                        {new osg::Vec2Array;
70                                numSeparator=0;
71                                for (size_t numLineChar=0; numLineChar < line.length(); numLineChar++)
72                                {
73                                        if(line.at(numLineChar)==separator) numSeparator++;
74                                }
75                                if(numSeparator!=numValues-1) //Number of Entries per Line is not correct
76                                {
77                                        OSG_ALWAYS<< "Inconsistency in file " << filePath << " detected. Please check this file." <<std::endl;
78                                        return 1;
79                                }
80                                valueStart=0;
81                                valueEnd=0;
82                                for (int j=0;j<numValues; j++)
83                                {
84                                        if(j!=numValues-1)
85                                        {
86                                                if((valueEnd=line.find(separator,valueStart))!=std::string::npos)
87                                                {
88                                                        valueString=line.substr(valueStart,valueEnd-valueStart);
89                                                        valueStart=valueEnd+1;
90                                                }
91                                        }
92                                        else valueString=line.substr(valueStart,line.size());
93
94                                        frustumValues[j]=atof(const_cast<char*>(valueString.c_str()));
95                                }
96                        }
97                }
98                inputFile.close();
99        }
100        else    //File couldn't be loaded
101        {
102                OSG_ALWAYS<< "Unable to open " << filePath << std::endl;
103                return 1;
104        }
105        return 0;
106}
107
108int DistortionSetupStrategyProjectSyntropy::readMeshDimensionsFromCSVFile(std::string filePath, int* meshRows, int* meshColumns)
109{
110        int tempRows=0, tempCols=0, numSeparator=0, numValues=6;
111        std::string line, valueString;
112        char separator=';';
113        size_t valueStart, valueEnd;
114
115        osgDB::ifstream inputFile (const_cast<char*>(filePath.c_str()));
116
117        if (inputFile.is_open())
118        {
119                inputFile.clear();
120                inputFile.seekg (0, std::ios::beg);
121
122                while (!inputFile.eof())
123                {
124                        getline (inputFile,line);
125
126                        if((line.size()>0) && (line.find('x')==std::string::npos))
127                        {
128                                numSeparator=0;
129                                for (size_t numLineChar=0; numLineChar < line.length(); numLineChar++)
130                                {
131                                        if(line.at(numLineChar)==separator) numSeparator++;
132                                }
133                                if(numSeparator!=numValues-1) //Number of Entries per Line is not correct
134                                {
135                                        OSG_ALWAYS<< "Inconsistency in file " << filePath << " detected. Please check this file." <<std::endl;
136                                        return 1;
137                                }
138                                //Get number of rows of the distortion grid, last valid line of input file contains actual value
139                                valueStart=line.rfind(separator,line.size());
140                                valueString=line.substr(valueStart+1,line.size()-valueStart-1);
141                                tempRows=atoi(const_cast<char*>(valueString.c_str()));
142                                if(tempRows>*meshRows) *meshRows=tempRows;
143
144                                //Get number of columns of the distortion grid, last valid line of input file contains actual value
145                                valueEnd=valueStart-1;
146                                valueStart=line.rfind(separator,valueEnd);
147                                valueString=line.substr(valueStart+1,valueEnd-valueStart);
148                                tempCols=atoi(const_cast<char*>(valueString.c_str()));
149                                if(tempCols>*meshColumns) *meshColumns=tempCols;
150                        }
151
152                }
153                inputFile.close();
154        }
155        else    //File couldn't be loaded
156        {
157                OSG_ALWAYS<< "Unable to open " << filePath << std::endl;
158                return 1;
159        }
160
161        *meshColumns+=1;
162        *meshRows+=1;
163
164        return 0;
165}
166
167int DistortionSetupStrategyProjectSyntropy::readMeshPointsFromCSVFile(std::string filePath, osg::Vec4Array* tmpMesh)
168{
169        int numValues=6;
170        std::string line, valueString;
171        char separator=';';
172        float* values = new float[numValues]; 
173        size_t valueStart, valueEnd;
174        osg::Vec2 tempVec2;
175        osg::Vec3 tempVec3;
176
177        osgDB::ifstream inputFile (const_cast<char*>(filePath.c_str()));
178
179        if (inputFile.is_open())
180        {
181                inputFile.clear();
182                inputFile.seekg (0, std::ios::beg);
183
184                while (!inputFile.eof())
185                {
186                        getline (inputFile,line);
187
188                        if((line.size()>0) && (line.find('x')==std::string::npos))
189                        {
190                                for (int i=0;i<numValues; i++) values[i]=0.0;
191
192                                valueStart=0;
193                                valueEnd=0;
194                                for (int j=0;j<numValues; j++)
195                                {
196                                        if(j!=numValues-1)
197                                        {
198                                                if((valueEnd=line.find(separator,valueStart))!=std::string::npos)
199                                                {
200                                                        valueString=line.substr(valueStart,valueEnd-valueStart);
201                                                        valueStart=valueEnd+1;
202                                                }
203                                        }
204                                        else valueString=line.substr(valueStart,line.size());
205
206                                        values[j]=atof(const_cast<char*>(valueString.c_str()));
207                                }
208
209                                // Store values into array
210                                tmpMesh->push_back(osg::Vec4(values[0], 1.0-values[1], values[2], 1.0-values[3]));
211                        }
212                }
213                inputFile.close();
214        }
215        else
216        {
217                OSG_ALWAYS<< "Unable to open " << filePath << std::endl;
218                return 1;
219        }
220
221        return 0;
222}
223
224void DistortionSetupStrategyProjectSyntropy::delegateDistortionSetup(osgViewer::DistortionSet* distortionSet)
225{
226        if(distortionSet == NULL)
227        {
228                OSG_ALWAYS<<"DistortionSetupStrategyProjectSyntropy::delegateDistortionSetup : Invalid DistortionSet"<<std::endl;
229                return;
230        }
231
232        if(      _blendmapFilename.empty() || _frustumFilename.empty() ||  _distortionFilename.empty() )
233        {
234                OSG_ALWAYS<<"DistortionSetupStrategyProjectSyntropy::delegateDistortionSetup : You have not specified the imput filenames correctly!"<<std::endl;
235                return;
236        }
237
238        if(     !osgDB::fileExists(_blendmapFilename) || !osgDB::fileExists(_frustumFilename) || !osgDB::fileExists(_distortionFilename) )
239        {
240                OSG_ALWAYS<<"DistortionSetupStrategyProjectionDesigner::delegateDistortionSetup : One of the specified input files does not exist!"<<std::endl;
241                return;
242        }
243
244        //OSG_ALWAYS<<"drin"<<std::endl;
245
246        if (_distortionInitialized==false )
247        {
248                _distortionInitialized=true;
249                distortionSet->dirtyMesh();
250                distortionSet->dirtyMatrix();
251
252
253                // ******************** //
254                // *** IntensityMap *** //
255                // ******************** //
256
257                osg::Image* intensityMap=NULL;
258                intensityMap=osgDB::readImageFile(_blendmapFilename);
259                osg::GraphicsContext::WindowingSystemInterface* wsi = osg::GraphicsContext::getWindowingSystemInterface();
260                if (!wsi)
261                {
262                        OSG_NOTICE<<"Error, no WindowSystemInterface available, cannot create windows."<<std::endl;
263                        return;
264                }
265
266                osg::GraphicsContext::ScreenIdentifier si;
267                si.readDISPLAY();
268
269                if (si.displayNum<0) si.displayNum = 0;
270
271                si.screenNum = 0; //Fixed value, may be replaced later
272
273                unsigned int width=0, height=0;
274                wsi->getScreenResolution(si, width, height);
275
276                if(intensityMap->s()!=width || intensityMap->t()!=height)
277                        intensityMap->scaleImage(width, height, intensityMap->r());
278
279                // Copy image data and flag as dirty to update texture.
280                osg::copyImage(intensityMap, 0, 0, 0, intensityMap->s(), intensityMap->t(), intensityMap->r(), distortionSet->getIntensityMap(), 0, 0, 0, true);
281                distortionSet->getIntensityMap()->dirty();
282
283                // ******************************* //
284                // *** Frustum and View Offset *** //
285                // ******************************* //
286
287                //....Read Files and set parameters
288                int numFrustumValues=16;
289                float* frustumValues = new float[numFrustumValues];
290                double zNear=1.0, zFar=1000.0;
291
292                readFrustumFromCSVFile(_frustumFilename, numFrustumValues, frustumValues);
293               
294                osg::Matrixd viewOffset=osg::Matrix::identity();
295                osg::Matrixd projectionOffset=osg::Matrixd();
296
297                // View Offset Parameters: x, y, z, heading, pitch, bank
298                // Translational Parameters are defines in millimeters (->Correction required?!)
299                // Coordinate System / Directions may be looked up in "Koordinatensystem.png", trans/rot order confirmed bei PS
300                osg::Matrixd rotViewOffset=osg::Matrixd();
301                rotViewOffset.makeRotate(
302                        osg::DegreesToRadians(frustumValues[3]), osg::Vec3(0,1,0),      // heading
303                        osg::DegreesToRadians(-frustumValues[4]), osg::Vec3(1,0,0),     // pitch
304                        osg::DegreesToRadians(frustumValues[5]), osg::Vec3(0,0,1));     // roll
305
306                osg::Matrixd transViewOffset=osg::Matrixd();
307                transViewOffset.makeTranslate( frustumValues[0], frustumValues[1], frustumValues[2]);
308
309                viewOffset = viewOffset * rotViewOffset; // * transViewOffset;
310               
311                //Frustum Parameters: Left, Right, Bottom, Top, zNear, zFar.
312                // Important: By definition of OpenGL, Left, Right, Bottom and Top must be set as tangens, multiplied by zNear!
313                projectionOffset.makeFrustum(frustumValues[10] * zNear, frustumValues[11] * zNear, frustumValues[12] * zNear, frustumValues[13] * zNear, zNear, zFar);
314
315                distortionSet->setViewOffset(viewOffset);
316                distortionSet->setProjectionOffset(projectionOffset);
317
318                // ******************************* //
319                // ******* Distortion Mesh ******* //
320                // ******************************* //
321
322                osg::Geometry* distortionMeshGeometry = distortionSet->getDistortionInternals()->getChild(osgViewer::DistortionSet::MESH)->asGeode()->getDrawable(0)->asGeometry();
323                if(distortionMeshGeometry)
324                {
325                        //*******************************************************************************************//
326                        //***    PRINT VERTEXARRAY/TEXCOORDARRAY for Debug Purposes                               ***//
327                        //***    both Arrays are listed in "HorizontalLine-after-HorizontalLine" order,           ***//
328                        //***    sorted from topleft (0,0,0 vertices; 0,0 texcoords) to bottomright               ***//
329                        //***    (1920,1080,0 vertices; 1,1 texcoords)                                                                                    ***//
330                        //*******************************************************************************************//
331                       
332#if 0
333                        osg::Vec3Array* vertices =  (osg::Vec3Array*) distortionMeshGeometry->getVertexArray();
334                        osg::Vec2Array* texcoords0 = (osg::Vec2Array*) distortionMeshGeometry->getTexCoordArray(0);
335
336                        for (osg::Vec3Array::iterator it = vertices->begin(); it != vertices->end(); ++it)
337                        {
338                                OSG_ALWAYS<<"Vertice "<<(*it).x()<<" "<<(*it).y()<<" "<<(*it).z()<<std::endl;
339                        }
340
341                        for (osg::Vec2Array::iterator it = texcoords0->begin(); it != texcoords0->end(); ++it)
342                        {
343                                OSG_ALWAYS<<"Texcoord "<<(*it).x()<<" "<<(*it).y()<<std::endl;
344                        }
345#endif
346
347                        //*******************************************************************************************//
348                        //***    MESH WARPING                                                                                                                                     ***//
349                        //***    Both Vertex Warping and Texcoord Warping is supported.
350                        //***    The input file contains . Although there might      ***//
351                        //***    be a preferred version for osgvisual, both options should be implemented in osg  ***//
352                        //*******************************************************************************************//
353
354                        // Exctract mesh dimensions from file and pass them to the container.
355
356                        int distortionMeshRows=0, distortionMeshColumns=0;
357                        readMeshDimensionsFromCSVFile(_distortionFilename, &distortionMeshRows, &distortionMeshColumns);
358
359                        distortionSet->setDistortionMeshRows(distortionMeshRows);
360                        distortionSet->setDistortionMeshColumns(distortionMeshColumns);
361
362                        // Read in the mesh arrays
363                        osg::Vec4Array* distortionMesh = new osg::Vec4Array;
364                        readMeshPointsFromCSVFile(_distortionFilename, distortionMesh);
365
366#if 0
367                        for (osg::Vec4Array::iterator it = distortionMesh->begin(); it != distortionMesh->end(); ++it)
368                        {
369                                OSG_ALWAYS<<"final vector: "<<(*it).x()<<" "<<(*it).y()<<" "<<(*it).z()<<" "<<(*it).w()<<std::endl;
370                        }
371#endif
372
373
374                        distortionSet->setDistortionMesh(distortionMesh);
375                        distortionSet->setDistortionMeshDimensions(distortionMeshRows, distortionMeshColumns);
376                }
377        }
378}
Note: See TracBrowser for help on using the repository browser.