source: osgVisual/trunk/src/dataIO/visual_dataIO.cpp @ 183

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

XML configuration now works also with dataIO cluster

File size: 12.7 KB
Line 
1/* -*-c++-*- osgVisual - Copyright (C) 2009-2010 Torben Dannhauer
2 *
3 * This library is based on OpenSceneGraph, open source and may be redistributed and/or modified under
4 * the terms of the OpenSceneGraph Public License (OSGPL) version 0.0 or
5 * (at your option) any later version.  The full license is in LICENSE file
6 * included with this distribution, and on the openscenegraph.org website.
7 *
8 * osgVisual requires for some proprietary modules a license from the correspondig manufacturer.
9 * You have to aquire licenses for all used proprietary modules.
10 *
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14 * OpenSceneGraph Public License for more details.
15*/
16
17#include "visual_dataIO.h"
18
19using namespace osgVisual;
20
21visual_dataIO::visual_dataIO()
22{
23        OSG_NOTIFY( osg::ALWAYS ) << "visual_dataIO constructed" << std::endl;
24
25        initialized = false;
26        clusterMode = osgVisual::dataIO_cluster::STANDALONE;
27        // Create Transport-Container:
28        slotContainer = new osgVisual::dataIO_transportContainer();
29}
30
31visual_dataIO::~visual_dataIO()
32{
33        // Delete all slots:
34        for(unsigned int i=0;i<dataSlots.size();i++)
35        {
36                delete dataSlots[i];
37        }
38        dataSlots.clear();
39       
40        OSG_NOTIFY( osg::ALWAYS ) << "visual_dataIO destructed" << std::endl;
41}
42
43visual_dataIO* visual_dataIO::getInstance()
44{
45        static visual_dataIO instance; 
46        return &instance; 
47};
48
49void visual_dataIO::init(osgViewer::Viewer* viewer_, osg::ArgumentParser& arguments_, std::string configFileName)
50{
51        OSG_NOTIFY( osg::ALWAYS ) << "visual_dataIO initialize..";
52
53        // Init variables
54        viewer = viewer_;
55
56        // Process XML configuration
57        this->configFileName = configFileName;
58        xmlNode *extLinkConfig=NULL;
59        if(!processXMLConfiguration(extLinkConfig))
60                OSG_FATAL << "ERROR: visual_dataIO::init() - Failed to initialize dataIO via XML configuration!";
61
62        // Create extLink.
63        #ifdef USE_EXTLINK_DUMMY
64                extLink = new dataIO_extLinkDummy( dataSlots );
65        #endif
66        #ifdef USE_EXTLINK_VCL
67                extLink = new dataIO_extLinkVCL( dataSlots );
68        #endif
69        extLink->init();
70
71       
72        // Install callbacks to perform DataIO activities every frame:
73        //// EventCallback at the absolute beginning of the frame
74        eventCallback = new dataIO_eventCallback(this);
75        viewer->getCamera()->setEventCallback( eventCallback );
76        //// FinalDrawCallback at the end of event and update handling, but BEFORE rendering the frame
77        finalDrawCallback = new dataIO_finalDrawCallback(this);
78        viewer->getCamera()->setFinalDrawCallback( finalDrawCallback );
79
80        initialized = true;
81}
82
83bool visual_dataIO::processXMLConfiguration(xmlNode* extLinkConfig_)
84{
85        // Init XML
86        xmlDoc* tmpDoc;
87        bool disabled;
88        xmlNode* config = util::getModuleXMLConfig( configFileName, "dataio", tmpDoc, disabled );
89        xmlNode* clusterConfig = NULL;
90
91        if( disabled)
92                OSG_NOTIFY( osg::ALWAYS ) << "..disabled by XML configuration file. dataIO can't be disabled. Ignoring." << std::endl;
93        else
94                OSG_NOTIFY( osg::ALWAYS ) << std::endl;
95
96        // extract configuration values
97        if(config)
98        {
99                xmlNode* a_node = config->children;
100
101                for (xmlNode *cur_node = a_node; cur_node; cur_node = cur_node->next)
102                {
103                        std::string node_name=reinterpret_cast<const char*>(cur_node->name);
104                        //OSG_ALWAYS << "----visual_distortion::processXMLConfiguration() - node type="<< cur_node->type <<", name=" << cur_node->name << std::endl;
105
106                        // Check for dataio node
107                        if(cur_node->type == XML_ELEMENT_NODE && node_name == "dataio")
108                        {
109                                // Extract cluster role
110                                xmlAttr  *attr = cur_node->properties;
111                                while ( attr ) 
112                                { 
113                                        std::string attr_name=reinterpret_cast<const char*>(attr->name);
114                                        std::string attr_value=reinterpret_cast<const char*>(attr->children->content);
115                                        if( attr_name == "clusterrole" )
116                                        {
117                                                if(attr_value == "master")
118                                                {
119                                                        OSG_NOTIFY( osg::ALWAYS ) << "Configure osgVisual as MASTER" << std::endl;
120                                                        clusterMode = osgVisual::dataIO_cluster::MASTER;
121                                                }
122                                                else if(attr_value == "slave")
123                                                {
124                                                        OSG_NOTIFY( osg::ALWAYS ) << "Configure osgVisual as SLAVE" << std::endl;
125                                                        clusterMode = osgVisual::dataIO_cluster::SLAVE;
126                                                        slotContainer = NULL;   // Slave only recieves container, therefor set this Pointer NULL (created instance will be deleted because it is an auto pointer).
127                                                }
128                                                else if(attr_value == "standalone")
129                                                {
130                                                        OSG_NOTIFY( osg::ALWAYS ) << "Configure osgVisual as STANDALONE" << std::endl;
131                                                        clusterMode = osgVisual::dataIO_cluster::STANDALONE;
132                                                }
133                                        }
134                                        attr = attr->next; 
135                                }       // WHILE attrib END
136                        }
137
138                        // Check for cluster node
139                        if(cur_node->type == XML_ELEMENT_NODE && node_name == "cluster")
140                        {
141                                // Pass cluster configuration to the used cluster implementation.
142                                // The implementation will use the configuration if it matches, otherwise falls back to dummy cluster
143                                clusterConfig = cur_node;
144                        }
145
146                        // Check for extLink node
147                        if(cur_node->type == XML_ELEMENT_NODE && node_name == "extlink")
148                        {
149                                // Check Attributes to determine if the dummy implementation or any other implementation must be instantiated
150
151                                // Pass XML attributes to extlink to analyse and configure it by extLink itself
152                        }
153
154                }       // FOR all nodes END
155
156
157
158                // Create Cluster.
159                #ifdef USE_CLUSTER_ASIO_TCP_IOSTREAM
160                        cluster = new dataIO_clusterAsioTcpIostream();
161                #endif
162                #ifdef USE_CLUSTER_ENET
163                        cluster = new dataIO_clusterENet();
164                #endif
165                if( !cluster.valid() || !clusterConfig || !cluster->init(clusterConfig, viewer, clusterMode, slotContainer, false) )
166                {
167                        cluster = new dataIO_clusterDummy();
168                        cluster->init(clusterConfig, viewer, clusterMode, slotContainer, false);
169                }
170
171
172
173                // clean up
174                xmlFreeDoc(tmpDoc); xmlCleanupParser();
175                return true;
176        }       // IF Config valid END
177        else
178        {
179                OSG_WARN << "ERROR: visual_data::processXMLConfiguration() - Module configuration not found" << std::endl;
180                return false;
181        }
182        return true;
183}
184
185void visual_dataIO::shutdown()
186{
187        if(initialized)
188        {
189                OSG_NOTIFY( osg::ALWAYS ) << "Shutdown visual_dataIO..." << std::endl;
190
191                viewer->getCamera()->removeEventCallback( eventCallback );
192                eventCallback = NULL;
193                viewer->getCamera()->setFinalDrawCallback( NULL );
194                finalDrawCallback = NULL;
195               
196                viewer = NULL;
197               
198
199                if(cluster.valid())
200                        cluster->shutdown();
201                if(extLink.valid())
202                extLink->shutdown();
203        }
204}
205
206void visual_dataIO::dataIO_eventCallback::operator()(osg::Node* node, osg::NodeVisitor* nv)
207{
208        // perform all actions for the eventDrawCallback.
209        OSG_NOTIFY( osg::INFO ) << "---- Executing EventCallback.." <<  std::endl;
210
211        switch( dataIO->clusterMode )
212        {
213                case osgVisual::dataIO_cluster::MASTER : 
214                        {
215                                dataIO->extLink->readTO_OBJvalues();
216                                dataIO->cluster->sendTO_OBJvaluesToSlaves(dataIO->calcViewMatrix());
217                        }
218                        break;
219                case osgVisual::dataIO_cluster::SLAVE : 
220                        {
221                                dataIO->cluster->readTO_OBJvaluesFromMaster();
222                        }
223                        break;
224                case osgVisual::dataIO_cluster::STANDALONE : 
225                        {
226                                dataIO->extLink->readTO_OBJvalues();
227                        }
228                        break;
229                default:
230                        OSG_NOTIFY( osg::FATAL ) << "ERROR: Unkown clustermode!" <<  std::endl;
231                        break;
232        };
233        traverse(node, nv);
234}
235
236void visual_dataIO::dataIO_finalDrawCallback::operator() (const osg::Camera& camera) const
237{
238        // perform all actions for the initialDrawCallback.
239        OSG_NOTIFY( osg::INFO ) << "---- Executing InitialDrawCallback.." << std::endl;
240
241        switch( dataIO->clusterMode )
242        {
243                case osgVisual::dataIO_cluster::MASTER : 
244                        {
245                                dataIO->extLink->writebackFROM_OBJvalues();
246                                dataIO->cluster->waitForAllReadyToSwap();
247                                dataIO->cluster->sendSwapCommand();
248                        }
249                        break;
250                case osgVisual::dataIO_cluster::SLAVE : 
251                        {
252                                dataIO->cluster->reportAsReadyToSwap();
253                                dataIO->cluster->waitForSwap();
254                        }
255                        break;
256                case osgVisual::dataIO_cluster::STANDALONE : 
257                        {
258                                dataIO->extLink->writebackFROM_OBJvalues();
259                        }
260                        break;
261                default:
262                        OSG_NOTIFY( osg::FATAL ) << "ERROR: visual_dataIO::dataIO_finalDrawCallback::operator() - Unkown clustermode!" <<  std::endl;
263                        break;
264        };
265}
266
267void* visual_dataIO::getSlotPointer(std::string variableName_, osgVisual::dataIO_slot::dataDirection direction_, osgVisual::dataIO_slot::varType variableTyp_ )
268{
269        // iterate through slotlist. If found, return pointer, else add slot to list and return pointer
270        for (unsigned int i=0; i<dataSlots.size(); i++)
271        {
272                // Check if this variable name&-type already exists
273                if( dataSlots[i]->variableName == variableName_ && dataSlots[i]->direction == direction_  && dataSlots[i]->variableType ==  variableTyp_)
274                {
275                        //OSG_NOTIFY( osg::INFO ) << "visual_dataIO::getSlotPointer() - Slot found at position " << i << std::endl;
276                        // Return pointer to the value
277                        return dataSlots[i];
278                }
279        }
280
281        // Slot does not exist -> add it to slot list
282        //OSG_NOTIFY( osg::INFO ) << "visual_dataIO::getSlotPointer() - Slot not found, will add as new slot " << std::endl;
283        dataIO_slot* newSlot = new dataIO_slot();
284        newSlot->variableName = variableName_;
285        newSlot->variableType = variableTyp_;
286        newSlot->value = 0;
287        newSlot->sValue = "";
288        dataSlots.push_back( newSlot );
289        return dataSlots.back();
290}
291
292double visual_dataIO::getSlotDataAsDouble(std::string variableName_, osgVisual::dataIO_slot::dataDirection direction_ )
293{
294        // iterate through slotlist. If found, return value
295        for (unsigned int i=0; i<dataSlots.size(); i++)
296        {
297                // Check if this variable name&-type already exists
298                if( dataSlots[i]->variableName == variableName_ && dataSlots[i]->direction == direction_  && dataSlots[i]->variableType == osgVisual::dataIO_slot::DOUBLE )
299                {
300                        //OSG_NOTIFY( osg::INFO ) << "visual_dataIO::getSlotDataAsDouble() - Slot found at position " << i << std::endl;
301                        return dataSlots[i]->value;
302                }
303        }
304        return 0;
305}
306
307std::string visual_dataIO::getSlotDataAsString(std::string variableName_, osgVisual::dataIO_slot::dataDirection direction_ )
308{
309        // iterate through slotlist. If found, return value
310        for (unsigned int i=0; i<dataSlots.size(); i++)
311        {
312                // Check if this variable name&-type already exists
313                if( dataSlots[i]->variableName == variableName_ && dataSlots[i]->direction == direction_  && dataSlots[i]->variableType == osgVisual::dataIO_slot::STRING )
314                {
315                        //OSG_NOTIFY( osg::INFO ) << "visual_dataIO::getSlotDataAsDouble() - Slot found at position " << i << std::endl;
316                        return dataSlots[i]->sValue;
317                }
318        }
319        return "";
320}
321
322osgVisual::dataIO_slot* visual_dataIO::setSlotData(std::string variableName_, osgVisual::dataIO_slot::dataDirection direction_, std::string sValue_ )
323{
324        bool slotFound = false;
325        // iterate through slotlist. If found, return pointer, else add slot to list
326        for (unsigned int i=0; i<dataSlots.size(); i++)
327        {
328                // Check if this variable name&-type already exists
329                if( dataSlots[i]->variableName == variableName_ && dataSlots[i]->direction == direction_ && dataSlots[i]->variableType ==  osgVisual::dataIO_slot::STRING)
330                {
331                        // Update value
332                        dataSlots[i]->sValue = sValue_;
333                        slotFound = true;
334                        return dataSlots[i];
335                }
336               
337        }
338
339        if (!slotFound)
340        {
341                // Slot does not exist -> add it to slot list
342                dataIO_slot* newSlot = new dataIO_slot();
343                newSlot->variableName = variableName_;
344                newSlot->direction = direction_;
345                newSlot->variableType = osgVisual::dataIO_slot::STRING;
346                newSlot->value = 0;
347                newSlot->sValue = sValue_;
348                dataSlots.push_back( newSlot );
349                return dataSlots.back();
350        }
351
352        return NULL;
353}
354
355osgVisual::dataIO_slot* visual_dataIO::setSlotData(std::string variableName_, osgVisual::dataIO_slot::dataDirection direction_, double value_ )
356{
357        // iterate through slotlist. If found, return pointer, else add slot to list
358        bool slotFound = false;
359        for (unsigned int i=0; i<dataSlots.size(); i++)
360        {
361                // Check if this variableName & -type already exists
362                if( dataSlots[i]->variableName == variableName_ && dataSlots[i]->direction == direction_ && dataSlots[i]->variableType ==  osgVisual::dataIO_slot::DOUBLE)
363                {
364                        // Update value
365                        //OSG_NOTIFY( osg::ALWAYS ) << "setSlotData: " << variableName_ << " - value: " << value_ << std::endl;
366                        dataSlots[i]->value = value_;
367                        slotFound = true;
368                        return dataSlots[i];
369                }       
370        }
371
372        if (!slotFound)
373        {
374                // Slot does not exist -> add it to slot list
375                dataIO_slot* newSlot = new dataIO_slot();
376                newSlot->variableName = variableName_;
377                newSlot->direction = direction_;
378                newSlot->variableType = osgVisual::dataIO_slot::DOUBLE;
379                newSlot->value = value_;
380                newSlot->sValue = "";
381                dataSlots.push_back( newSlot );
382                return dataSlots.back();
383        }
384
385        return NULL;
386}
387
388osg::Matrixd visual_dataIO::calcViewMatrix()
389{
390        return viewer->getCameraManipulator()->getInverseMatrix();
391}
Note: See TracBrowser for help on using the repository browser.