00001
00002
00004
00005 #include <X3DTK/memreleaser.h>
00006 #include <X3DTK/X3D/scenegraph.h>
00007 #include <X3DTK/X3D/glbuilder.h>
00008 #include <X3DTK/X3D/scenesaver.h>
00009 #include <X3DTK/X3D/bboxupdater.h>
00010
00011
00012
00013
00014 #include <animal/X3DTK/X3D/engine/engineWalker.h>
00015 #include <animal/X3DTK/X3D/engine/engineLoaderVisitor.h>
00016 #include <animal/X3DTK/X3D/engine/engineLoader.h>
00017 #include <animal/X3DTK/X3D/engine/glBuilderEngineNodeVisitor.h>
00018 #include <animal/X3DTK/Qt/mainControllerGUI/MainController.h>
00019 #include <animal/engine/engine.h>
00020 #include <animal/event/keyEvent.h>
00021 #include <animal/event/mouseEvent.h>
00022 #include <animal/X3DTK/X3D/massSpringNode/massSpringNode.h>
00023
00024 #include "mainScene.h"
00025 #include <iostream>
00026 using std::cout;
00027 using std::endl;
00028 using std::cerr;
00029
00030
00031 namespace X3DTK
00032 {
00033
00035 MainScene::MainScene()
00036 : x3dscene(NULL)
00037 , glscene(NULL)
00038 , x3dloader(NULL)
00039 , mainController(NULL)
00040 , m_selectedNode(NULL)
00041 {
00042
00043 engineLoader = new X3D::EngineLoader(&allEngineNodes, &kinematicEngines, &dynamicEngines, &collisionEngines);
00044
00045
00046
00047
00048
00049
00050
00051
00052 x3dscene = new X3D::Scene();
00053 bbupdater = new X3D::BBoxUpdater();
00054 buildGL();
00055
00056 }
00057
00059 MainScene:: ~MainScene()
00060 {
00061 releaseNode(x3dscene);
00062 releaseNode(glscene);
00063 x3dscene = NULL;
00064 glscene = NULL;
00065
00066 if (x3dloader)
00067 {
00068
00069 x3dloader = NULL;
00070 }
00071
00072
00073
00074
00075
00076
00077
00078
00079
00080
00081
00082
00083
00084
00085
00086
00087
00088
00089
00090
00091
00092
00093
00094
00095
00096
00097
00098
00099
00100
00101
00102 }
00103
00104
00106 void MainScene::load(const char *file, bool fileValidation)
00107 {
00108
00109 if (!x3dloader)
00110 {
00111 std::cerr<<"Warning MainScene::load(): impossible to load because the x3dloader is NULL."<<std::endl;
00112 return;
00113 }
00114 releaseNode(x3dscene);
00115 x3dscene = NULL;
00116 x3dscene = x3dloader->load(file, fileValidation);
00117
00118
00119 engineLoader->initialize(x3dscene);
00120
00121
00122 buildGL();
00123
00124 }
00125
00127 void MainScene::load(const char *file, X3D::X3DNode * node, bool fileValidation)
00128 {
00129 if (!node)
00130 {
00131 std::cerr<< "Warning: impossible to insert. The node from where you want to insert new nodes is NULL."<< std::endl;
00132 return;
00133 }
00134
00135 if (node && dynamic_cast<X3D::X3DGroupingNode *>(node) == NULL)
00136 {
00137 std::cerr<< "Warning: impossible to insert. The node from where you want to insert new nodes is not an X3D::X3DGroupingNode."<< std::endl;
00138 return;
00139 }
00140
00141
00142 if (!x3dloader)
00143 {
00144 std::cerr<<"Warning MainScene::load(): impossible to load because the x3dloader is NULL."<<std::endl;
00145 return;
00146 }
00147 X3D::Scene * sceneTmp = x3dloader->load(file, fileValidation);
00148
00149
00150 MFNode childrenList = sceneTmp->getChildren();
00151 for(MFNode::iterator it = childrenList.begin(); it != childrenList.end();++it)
00152 {
00153 engineLoader->initialize(*it);
00154 pastNode((*it), node);
00155 }
00156
00157 delete sceneTmp;
00158 }
00159
00161 bool MainScene::pastNode(X3DAbstractNode* node, X3DAbstractNode* parentNode)
00162 {
00163 if (!node)
00164 {
00165 std::cerr<< "Warning MainScene::pastNode(): impossible to past. The node you want to past is NULL."<< std::endl;
00166 return false;
00167 }
00168
00169 if (!parentNode)
00170 {
00171 std::cerr<< "Warning MainScene::pastNode(): impossible to past. The parent node where you want to past a node is NULL."<< std::endl;
00172 return false;
00173 }
00174
00175 if (isADescendant(parentNode, node))
00176 {
00177 std::cerr<< "Warning MainScene::pastNode(): impossible to past. The parentNode is a descendant of the node you want to past."<< std::endl;
00178 return false;
00179 }
00180
00181 if (parentNode && dynamic_cast<X3D::X3DGroupingNode *>(parentNode) == NULL)
00182 {
00183 std::cerr<< "Warning MainScene::pastNode(): impossible to past. The node from where you want to past new nodes is not an X3D::X3DGroupingNode."<< std::endl;
00184 return false;
00185 }
00186
00187 parentNode->setChild(node);
00188
00189
00190 SFString s = node->getName();
00191 if (s=="")
00192 {
00193 node->setName(node->getType()->getName());
00194 }
00195
00196
00197 engineLoader->initialize(node);
00198
00199
00200 buildGL();
00201
00202 return true;
00203 }
00204
00209 bool MainScene::cutNode(X3DAbstractNode* node, X3DAbstractNode* parentNode)
00210 {
00211 if (!node)
00212 {
00213 std::cerr<< "Warning MainScene::cutNode(): impossible to cut. The node you want to cut is NULL."<< std::endl;
00214 return false;
00215 }
00216
00217 if (dynamic_cast<X3D::X3DChildNode *>(node) == NULL)
00218 {
00219 std::cerr<< "Warning MainScene::cutNode(): impossible to cut. The node you want to cut is not an X3D::X3DChildNode."<< std::endl;
00220 return false;
00221 }
00222
00223 engineLoader->release(node);
00224 if (parentNode)
00225 {
00226
00227 parentNode->removeChild(node);
00228
00229
00230
00231
00232
00233
00234
00235
00236 }
00237 else if (x3dscene==node)
00238 {
00239
00240 MFNode childrenList = x3dscene->getChildren();
00241 for(MFNode::iterator it = childrenList.begin(); it != childrenList.end();++it)
00242 {
00243
00244 deleteNode(*it, x3dscene);
00245 }
00246 }
00247
00248
00249 buildGL();
00250
00251 return true;
00252
00253 }
00254
00260 void MainScene::deleteNode(X3DAbstractNode* node, X3DAbstractNode* parentNode)
00261 {
00262 if(cutNode(node, parentNode))
00263 {
00264
00265
00266
00267
00268 if (mainController && !isADescendant(node, x3dscene))
00269 {
00270 MFNode childrenList = node->getChildList();
00271 for(MFNode::iterator it = childrenList.begin(); it != childrenList.end();++it)
00272 mainController->removeX3DQtMap(dynamic_cast<X3D::X3DNode *>(*it));
00273 mainController->removeX3DQtMap(node);
00274 }
00275
00276
00277 releaseNode(node);
00278 }
00279 }
00280
00284 void MainScene::releaseNode(X3DAbstractNode* node)
00285 {
00286 if (node==x3dscene)
00287 {
00288
00289 MFNode childrenList = x3dscene->getChildren();
00290 for(MFNode::iterator it = childrenList.begin(); it != childrenList.end();++it)
00291 deleteNode(*it, x3dscene);
00292 }
00293 else
00294 {
00295 if( X3D::EngineNode* e=dynamic_cast<X3D::EngineNode*>(node) )
00296 {
00297 glUpdates.erase(e);
00298 }
00299 MemReleaser releaser;
00300 releaser.release(node);
00301 }
00302 }
00303
00305 void MainScene::draw()
00306 {
00307
00308
00309
00310 for( AnimalEngines::iterator i=animalEngines.begin(); i!=animalEngines.end(); ++i )
00311 {
00312 if((*i)->drawEngine)
00313 (*i)->draw();
00314 if((*i)->drawBBox)
00315 (*i)->drawBoundingBox();
00316 }
00317
00318 if (glscene)
00319 {
00320
00321 glPushAttrib(GL_ALL_ATTRIB_BITS);
00322
00323 renderer.render(glscene);
00324 glPopAttrib();
00325 }
00326 }
00327
00329 void MainScene::save(const char *file)
00330 {
00331
00332 for( X3D::EngineNodes::iterator i= allEngineNodes.begin(); i!=allEngineNodes.end(); ++i )
00333 (*i)->close();
00334
00335 for( X3D::EngineNodes::reverse_iterator i= allEngineNodes.rbegin(); i!=allEngineNodes.rend(); ++i )
00336 (*i)->postClose();
00337
00338 X3D::SceneSaver sceneSaver;
00339 sceneSaver.saveAs(x3dscene, file);
00340 }
00341
00343 void MainScene::reset()
00344 {
00345
00346 for( AnimalEngines::iterator i= animalEngines.begin(); i!=animalEngines.end(); ++i )
00347 if((*i)->resetEngine)
00348 (*i)->reset();
00349
00350
00351 for( X3D::EngineNodes::iterator i= allEngineNodes.begin(); i!=allEngineNodes.end(); ++i )
00352 (*i)->reset();
00353
00354 for( X3D::EngineNodes::reverse_iterator i= allEngineNodes.rbegin(); i!=allEngineNodes.rend(); ++i )
00355 (*i)->postReset();
00356
00357 updateGL();
00358 }
00359
00361 void MainScene::move(double dt)
00362 {
00363
00364
00365
00366 for( AnimalEngines::iterator i= animalEngines.begin(); i!=animalEngines.end(); ++i )
00367 if ((*i)->moveEngine)
00368 (*i)->move(dt);
00369
00370 for( X3D::EngineNodes::iterator i= allEngineNodes.begin(); i!=allEngineNodes.end(); ++i )
00371 {
00372 if( (*i)->m_animate )
00373 (*i)->animate(dt);
00374 }
00375 for( X3D::EngineNodes::reverse_iterator i= allEngineNodes.rbegin(); i!=allEngineNodes.rend(); ++i )
00376 {
00377 if( (*i)->m_animate )
00378 (*i)->postAnimate(dt);
00379 }
00380
00381 updateGL();
00382 }
00383
00386 bool MainScene::computeBbox()
00387 {
00388
00389
00390
00391 for( X3D::EngineNodes::iterator i= allEngineNodes.begin(); i!=allEngineNodes.end(); ++i )
00392 {
00393 (*i)->updateBoundingBox();
00394
00395 }
00396
00397
00398 bbupdater->update(x3dscene);
00399 SFVec3f center = x3dscene->getBBoxCenter();
00400 SFVec3f size = x3dscene->getBBoxSize();
00401
00402 SFVec3f A = center + 0.5f*size;
00403 SFVec3f B = center - 0.5f*size;
00404
00405 if (A.x < B.x)
00406 {
00407 min.x = A.x;
00408 max.x = B.x;
00409 }
00410 else
00411 {
00412 min.x = B.x;
00413 max.x = A.x;
00414 }
00415
00416 if (A.y < B.y)
00417 {
00418 min.y = A.y;
00419 max.y = B.y;
00420 }
00421 else
00422 {
00423 min.y = B.y;
00424 max.y = A.y;
00425 }
00426
00427 if (A.z < B.z)
00428 {
00429 min.z = A.z;
00430 max.z = B.z;
00431 }
00432 else
00433 {
00434 min.z = B.z;
00435 max.z = A.z;
00436 }
00437
00438
00439 float minX, minY, minZ, maxX, maxY, maxZ;
00440
00441 for( AnimalEngines::iterator i= animalEngines.begin(); i!=animalEngines.end(); ++i )
00442 {
00443 (*i)->getBoundingBox(minX, minY, minZ, maxX, maxY, maxZ);
00444 if (minX < min.x)
00445 min.x = minX;
00446 if (minY < min.y)
00447 min.y = minY;
00448 if (minZ < min.z)
00449 min.z = minZ;
00450 if (max.x < maxX)
00451 max.x = maxX;
00452 if (max.y < maxY)
00453 max.y = maxY;
00454 if (max.z < maxZ)
00455 max.z = maxZ;
00456 }
00457
00458
00459 return true;
00460 }
00461
00462
00464 void MainScene::addEngine( animal::Engine * engine)
00465 {
00466 animalEngines.push_back(engine);
00467 engine->init();
00468 computeBbox();
00469 }
00470
00472 void MainScene::removeEngine(animal::Engine* engine)
00473 {
00474 animalEngines.remove(engine);
00475 computeBbox();
00476 }
00477
00479 void MainScene::clearEngines()
00480 {
00481 animalEngines.clear();
00482 computeBbox();
00483 }
00484
00486 void MainScene::updateGL()
00487 {
00488 for( GLUpdates::iterator u=glUpdates.begin(); u!=glUpdates.end(); ++u )
00489 {
00490 for( GLNodeList::iterator g=(*u).second.begin(); g!=(*u).second.end(); ++g )
00491 {
00492 (*g)->update();
00493 }
00494 }
00495 computeBbox();
00496
00497 }
00498
00502 void MainScene::buildGL()
00503 {
00504
00505
00506 releaseNode(glscene);
00507 glscene = NULL;
00508 X3D::GLBuilder builder;
00509 builder.setComponentVisitor(new X3D::GLBuilderEngineNodeVisitor());
00510 glscene = builder.build(x3dscene);
00511
00512
00513 GL::X3DGLMapBuilder x3dGLMapBuilder;
00514 x3dGLMap = *x3dGLMapBuilder.build(glscene);
00515 glUpdates.clear();
00516
00517
00518 for( X3DGLMap::iterator i= x3dGLMap.begin(); i!=x3dGLMap.end(); ++i )
00519 {
00520
00521 X3DTK::X3D::EngineNode* engineNode = dynamic_cast<X3DTK::X3D::EngineNode*>((*i).first);
00522 if(engineNode)
00523 {
00524
00525 typedef X3DTK::X3D::X3D_X3DNodeList NodeList;
00526 NodeList outputs;
00527 outputs.clear();
00528 engineNode->declareOutputs(outputs);
00529
00530 for(NodeList::iterator n=outputs.begin(); n!=outputs.end(); ++n )
00531 {
00532 if( X3DTK::X3D::Coordinate* c = dynamic_cast<X3DTK::X3D::Coordinate*>(*n) )
00533 {
00534
00535 MFNode parents = c->getParentList();
00536 for( MFNode::iterator p=parents.begin(); p!=parents.end(); ++p)
00537 {
00538 if( X3DTK::X3D::X3DGeometryNode* g = dynamic_cast<X3DTK::X3D::X3DGeometryNode*>(*p) )
00539 {
00540
00541 for (std::list<GL::X3DNode *>::iterator i= x3dGLMap[g].begin(); i!=x3dGLMap[g].end(); ++i)
00542 {
00543
00544 glUpdates[engineNode].push_back(*i);
00545 }
00546 }
00547 }
00548 }
00549 else if( X3DTK::X3D::Transform* t = dynamic_cast<X3DTK::X3D::Transform*>(*n) )
00550 {
00551
00552 for (std::list<GL::X3DNode *>::iterator i= x3dGLMap[t].begin(); i!=x3dGLMap[t].end(); ++i)
00553 {
00554
00555 glUpdates[engineNode].push_back(*i);
00556 }
00557 }
00558 else if( dynamic_cast<X3DTK::X3D::MassSpringNode*>(*n) )
00559 {
00560
00561 }
00562 else
00563 {
00564
00565
00566 std::cout<<"MainScene::buildGL, can not find gl update to perform for output "<< (*n)->getName() << std::endl;
00567 }
00568 }
00569
00570 }
00571 else
00572 {
00573
00574 }
00575 }
00576
00577 }
00578
00579
00581 bool MainScene::isADescendant(X3DAbstractNode* node1, X3DAbstractNode* node2)
00582 {
00583 if (node1 == node2)
00584 return true;
00585
00586 if (!node2 || !node1)
00587 return false;
00588
00589 MFNode childrenList = node2->getChildList();
00590 for(MFNode::iterator it = childrenList.begin(); it != childrenList.end();++it)
00591 if(isADescendant(node1,static_cast<X3DTK::X3D::X3DNode*>(*it)))
00592 return true;
00593 return false;
00594 }
00595
00596
00597 void MainScene::keyPressEvent(animal::KeyEvent *e)
00598 {
00599 for( AnimalEngines::iterator i= animalEngines.begin(); i!=animalEngines.end(); ++i )
00600 (*i)->keyPressEvent(e);
00601 }
00602
00603 void MainScene::mouseDoubleClickEvent(animal::MouseEvent * e)
00604 {
00605 for( AnimalEngines::iterator i= animalEngines.begin(); i!=animalEngines.end(); ++i )
00606 (*i)->mouseDoubleClickEvent(e);
00607 }
00608
00609 void MainScene::mouseMoveEvent(animal::MouseEvent * e)
00610 {
00611 for( AnimalEngines::iterator i= animalEngines.begin(); i!=animalEngines.end(); ++i )
00612 (*i)->mouseMoveEvent(e);
00613 }
00614
00615 void MainScene::mousePressEvent(animal::MouseEvent * e)
00616 {
00617 for( AnimalEngines::iterator i= animalEngines.begin(); i!=animalEngines.end(); ++i )
00618 (*i)->mousePressEvent(e);
00619 }
00620
00621 void MainScene::mouseReleaseEvent(animal::MouseEvent * e)
00622 {
00623 for( AnimalEngines::iterator i= animalEngines.begin(); i!=animalEngines.end(); ++i )
00624 (*i)->mouseReleaseEvent(e);
00625 }
00626
00627
00628
00629 animal::ConstrainedItem* MainScene::pickPoint(float origin[3], float direction[3],
00630 float threshold )
00631 {
00632 animal::ConstrainedItem* item = 0;
00633
00634
00635 AnimalEngines::iterator e=animalEngines.begin(), eend=animalEngines.end();
00636 while( e != eend && item==0 )
00637 {
00638
00639 item = (*e)->pickPoint( origin, direction, threshold );
00640 ++e;
00641 }
00642
00643 X3D::EngineNodes::iterator en=allEngineNodes.begin(), enend=allEngineNodes.end();
00644 while( en != enend && item==0 )
00645 {
00646
00647 item = (*en)->pickPoint( origin, direction, threshold );
00648 ++en;
00649 }
00650
00651
00652 return item;
00653 }
00654
00655
00656 void MainScene::setSelectedNode( X3D::X3DBoundedObject * n )
00657 {
00658 m_selectedNode = n;
00659 renderer.setBoundedObject(m_selectedNode);
00660 }
00661
00662
00663 }