fixed: auto_ptr -> unique_ptr
[opensg.git] / Source / System / FileIO / WRL / OSGVRMLWriteAction.cpp
blob860dd93f69e9c873572dcd2b6b94befb2ae30b4c
1 /*---------------------------------------------------------------------------*\
2 * OpenSG *
3 * *
4 * *
5 * Copyright (C) 2000-2002 by the OpenSG Forum *
6 * *
7 * www.opensg.org *
8 * *
9 * contact: dirk@opensg.org, gerrit.voss@vossg.org, jbehr@zgdv.de *
10 * *
11 \*---------------------------------------------------------------------------*/
12 /*---------------------------------------------------------------------------*\
13 * License *
14 * *
15 * This library is free software; you can redistribute it and/or modify it *
16 * under the terms of the GNU Library General Public License as published *
17 * by the Free Software Foundation, version 2. *
18 * *
19 * This library is distributed in the hope that it will be useful, but *
20 * WITHOUT ANY WARRANTY; without even the implied warranty of *
21 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU *
22 * Library General Public License for more details. *
23 * *
24 * You should have received a copy of the GNU Library General Public *
25 * License along with this library; if not, write to the Free Software *
26 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. *
27 * *
28 \*---------------------------------------------------------------------------*/
29 /*---------------------------------------------------------------------------*\
30 * Changes *
31 * *
32 * *
33 * *
34 * *
35 * *
36 * *
37 \*---------------------------------------------------------------------------*/
39 //---------------------------------------------------------------------------
40 // Includes
41 //---------------------------------------------------------------------------
43 #include <cstdlib>
44 #include <cstdio>
46 #include "OSGConfig.h"
48 #include "OSGLog.h"
49 #include "OSGFieldContainer.h"
50 #include "OSGNode.h"
51 #include "OSGNodeCore.h"
52 #include "OSGGroup.h"
53 #include "OSGGeometry.h"
54 #include "OSGTriangleIterator.h"
55 #include "OSGPointIterator.h"
56 #include "OSGComponentTransform.h"
57 //#include "OSGGeoPropPtrs.h"
58 #include "OSGSimpleMaterial.h"
59 #include "OSGMaterialGroup.h"
60 #include "OSGAction.h"
61 #include "OSGVRMLWriteAction.h"
62 #include "OSGNameAttachment.h"
63 #include "OSGTextureObjChunk.h"
64 #include "OSGImage.h"
65 #include "OSGImageFileHandler.h"
66 #include "OSGSimpleGeometry.h"
67 #include "OSGSceneFileHandler.h"
69 #include "OSGGL.h"
71 #include "functional"
73 OSG_USING_NAMESPACE
76 /***************************************************************************\
77 * Description *
78 \***************************************************************************/
80 /*! \class OSG::VRMLWriteAction
81 \ingroup GrpSystemAction
83 The action class for writing VRML files.
87 /***************************************************************************\
88 * Types *
89 \***************************************************************************/
91 VRMLWriteAction::ActionInitializer::ActionInitializer(void)
93 addPostFactoryInitFunction(&VRMLWriteAction::initializeAction);
94 addPreFactoryExitFunction (&VRMLWriteAction::terminateAction );
97 VRMLWriteAction::ActionInitializer::~ActionInitializer(void)
101 VRMLWriteAction::FCInfo::FCInfo(void) :
102 _iTimesUsed(0 ),
103 _bOwnName (false),
104 _szName (NULL ),
105 _bWritten (false)
109 VRMLWriteAction::FCInfo::FCInfo(const FCInfo &source) :
110 _iTimesUsed(source._iTimesUsed),
111 _bOwnName (source._bOwnName ),
112 _szName (NULL ),
113 _bWritten (source._bWritten )
115 if(_bOwnName == true)
117 osgStringDup(source._szName, _szName);
121 VRMLWriteAction::FCInfo::~FCInfo(void)
123 if(_bOwnName == true)
124 delete [] _szName;
127 Char8 VRMLWriteAction::FCInfo::mapChar(Char8 c)
129 // These are taken from the VRML97 reference document
130 static char badchars[] = {
131 0x22, 0x23, 0x27, 0x2c, 0x2e, 0x5b, 0x5c, 0x5d, 0x7b, 0x7d, 0x7f
134 if (c <= 0x20) return '_';
136 for(UInt16 i = 0; i < sizeof(badchars); ++i)
137 if(c == badchars[i])
138 return '_';
140 return c;
143 void VRMLWriteAction::FCInfo::convertName(Char8 *&szName)
145 if(szName == NULL)
146 return;
148 for(UInt32 i = 0; i < strlen(szName); i++)
150 szName[i] = mapChar(szName[i]);
153 // first char a number a plus or a minus? add an _
154 if((szName[0] >= 0x30 && szName[0] <= 0x39) ||
155 szName[0] == 0x2b || szName[0] == 0x2d)
157 Char8 *newstring = new char [strlen(szName) + 2];
159 newstring[0] = '_';
160 strcpy(newstring + 1, szName);
161 delete[] szName;
162 szName = newstring;
166 void VRMLWriteAction::FCInfo::setName(const Char8 *szName)
168 osgStringDup(szName, _szName);
169 convertName(_szName);
170 _bOwnName = true;
173 void VRMLWriteAction::FCInfo::buildName(const Char8 *szTypename,
174 UInt32 uiContainerId)
176 if(_szName != NULL)
177 return;
179 if(szTypename != NULL)
181 _szName = new Char8[strlen(szTypename) + 32];
183 sprintf(_szName, "%s_%u", szTypename, uiContainerId);
185 else
187 _szName = new Char8[64];
189 sprintf(_szName, "UType_%u", uiContainerId);
192 _bOwnName = true;
195 void VRMLWriteAction::FCInfo::incUse(void)
197 _iTimesUsed++;
200 UInt32 VRMLWriteAction::FCInfo::getUse(void) const
202 return _iTimesUsed;
205 const Char8 *VRMLWriteAction::FCInfo::getName(void) const
207 return _szName;
210 bool VRMLWriteAction::FCInfo::getWritten(void) const
212 return _bWritten;
215 void VRMLWriteAction::FCInfo::setWritten(void)
217 _bWritten = true;
220 Int32 VRMLWriteAction::FCInfo::clear(void)
222 _iTimesUsed = 0;
224 if(_bOwnName == true)
226 delete [] _szName;
229 _bOwnName = false;
230 _szName = NULL;
231 _bWritten = false;
233 return 0;
236 /***************************************************************************\
237 * Class variables *
238 \***************************************************************************/
240 VRMLWriteAction * VRMLWriteAction::_prototype = NULL;
242 std::vector<Action::Functor> *VRMLWriteAction::_defaultEnterFunctors;
243 std::vector<Action::Functor> *VRMLWriteAction::_defaultLeaveFunctors;
245 VRMLWriteAction::ActionInitializer VRMLWriteAction::_actionInitializer;
248 /***************************************************************************\
249 * Class methods *
250 \***************************************************************************/
254 /*-------------------------------------------------------------------------*\
255 - public -
256 \*-------------------------------------------------------------------------*/
258 void VRMLWriteAction::registerEnterDefault(const FieldContainerType &type,
259 const Action::Functor &func)
261 if(_defaultEnterFunctors == NULL)
262 _defaultEnterFunctors = new std::vector<Action::Functor>;
264 while(type.getId() >= _defaultEnterFunctors->size())
266 _defaultEnterFunctors->push_back(&Action::_defaultEnterFunction);
269 (*_defaultEnterFunctors)[type.getId()] = func;
272 void VRMLWriteAction::registerLeaveDefault(const FieldContainerType &type,
273 const Action::Functor &func)
275 if(_defaultLeaveFunctors == NULL)
276 _defaultLeaveFunctors = new std::vector<Action::Functor>;
278 while(type.getId() >= _defaultLeaveFunctors->size())
280 _defaultLeaveFunctors->push_back(&Action::_defaultLeaveFunction);
283 (*_defaultLeaveFunctors)[type.getId()] = func;
286 void VRMLWriteAction::setPrototype(VRMLWriteAction *proto)
288 _prototype = proto;
291 VRMLWriteAction *VRMLWriteAction::getPrototype( void )
293 return _prototype;
296 /*-------------------------------------------------------------------------*\
297 - protected -
298 \*-------------------------------------------------------------------------*/
301 /*-------------------------------------------------------------------------*\
302 - private -
303 \*-------------------------------------------------------------------------*/
305 Action::ResultE VRMLWriteAction::writeGroupEnter(NodeCore * const ,
306 Action *pAction)
308 VRMLWriteAction *pWriter = dynamic_cast<VRMLWriteAction *>(pAction);
310 Node *pNode = pAction->getActNode();
312 if(pWriter == NULL)
314 return Action::Quit;
317 FDEBUG(("Write Group Enter 0x%04x\n", pWriter->getMode()));
319 if(pWriter->getMode() == VRMLWriteAction::OSGCollectFC)
321 pWriter->addNodeUse(pNode);
323 else
325 FILE *pFile = pWriter->getFilePtr();
327 if(pFile == NULL)
329 return Action::Quit;
332 pWriter->updateProgress();
334 NodeCore *pCore = pNode->getCore();
336 FCInfo *pInfo = pWriter->getInfo(pNode);
337 FCInfo *pCoreInfo = pWriter->getInfo(pCore);
339 if(pInfo == NULL || pCoreInfo == NULL)
341 FWARNING(("Info missing %p %p\n",
342 static_cast<void *>(pInfo),
343 static_cast<void *>(pCoreInfo)));
344 return Action::Quit;
347 if(pCoreInfo->getUse() > 0 &&
348 pCoreInfo->getWritten() == true)
350 pWriter->printIndent();
351 fprintf(pFile, "Group # osg shared %s\n", pCoreInfo->getName());
353 // pWriter->setCurrentUse(true);
355 else if((pCoreInfo->getName() != NULL) &&
356 (pCoreInfo->getName()[0] != '\0'))
358 pWriter->printIndent();
359 fprintf(pFile, "DEF %s Group\n", pCoreInfo->getName());
361 pCoreInfo->setWritten();
363 else if((pInfo->getName() != NULL) &&
364 (pInfo->getName()[0] != '\0'))
366 pWriter->printIndent();
367 fprintf(pFile, "DEF %s Group\n", pInfo->getName());
369 pInfo->setWritten();
371 else
373 pWriter->printIndent();
374 fprintf(pFile, "Group\n");
377 pWriter->printIndent();
378 fprintf(pFile, "{\n");
380 if(pNode->getNChildren() != 0)
382 pWriter->incIndent(4);
384 pWriter->printIndent();
385 fprintf(pFile, "children [\n");
387 pWriter->incIndent(4);
391 return Action::Continue;
394 Action::ResultE VRMLWriteAction::writeGroupLeave(NodeCore * const ,
395 Action *pAction)
397 VRMLWriteAction *pWriter = dynamic_cast<VRMLWriteAction *>(pAction);
399 Node *pNode = pAction->getActNode();
401 if(pWriter == NULL)
403 return Action::Quit;
406 FDEBUG(("Write Group Leave 0x%04x\n", pWriter->getMode()));
408 if(pWriter->getMode() != VRMLWriteAction::OSGCollectFC)
410 FILE *pFile = pWriter->getFilePtr();
412 if(pFile == NULL)
414 return Action::Quit;
417 if(pWriter->isCurrentUse() == false)
419 if(pNode->getNChildren() != 0)
421 pWriter->decIndent(4);
423 pWriter->printIndent();
424 fprintf(pFile, "]\n");
426 pWriter->decIndent(4);
429 pWriter->printIndent();
430 fprintf(pFile, "}\n");
433 pWriter->setCurrentUse(false);
436 return Action::Continue;
439 Action::ResultE VRMLWriteAction::writeComponentTransformEnter(NodeCore * const,
440 Action *pAction)
442 VRMLWriteAction *pWriter = dynamic_cast<VRMLWriteAction *>(pAction);
443 Node *pNode = pAction->getActNode();
444 ComponentTransform *pTrans =
445 dynamic_cast<ComponentTransform *>(pNode->getCore());
447 Real32 rQX;
448 Real32 rQY;
449 Real32 rQZ;
450 Real32 rQW;
452 if(pWriter == NULL)
454 return Action::Quit;
457 FDEBUG(("Write ComponentTransform Enter 0x%04x\n", pWriter->getMode()));
459 if(pWriter->getMode() == VRMLWriteAction::OSGCollectFC)
461 pWriter->addNodeUse(pNode);
463 else
465 FILE *pFile = pWriter->getFilePtr();
467 if(pFile == NULL)
469 return Action::Quit;
472 pWriter->updateProgress();
474 FCInfo *pInfo = pWriter->getInfo(pNode);
476 if(pInfo == NULL)
478 return Action::Quit;
481 if((pInfo->getName() != NULL ) &&
482 (pInfo->getWritten() == false) &&
483 (pInfo->getName()[0] != '\0'))
485 pWriter->printIndent();
486 fprintf(pFile, "DEF %s Transform\n", pInfo->getName());
488 pInfo->setWritten();
490 else
492 pWriter->printIndent();
493 fprintf(pFile, "Transform\n");
496 pWriter->printIndent();
497 fprintf(pFile, "{\n");
499 pWriter->incIndent(4);
501 pWriter->printIndent();
502 fprintf(pFile, "center %f %f %f\n",
503 pTrans->getCenter()[0],
504 pTrans->getCenter()[1],
505 pTrans->getCenter()[2]);
507 pTrans->getRotation().getValueAsAxisRad(rQX, rQY, rQZ, rQW);
509 pWriter->printIndent();
510 fprintf(pFile, "rotation %f %f %f %f\n",
511 rQX, rQY, rQZ, rQW);
513 pWriter->printIndent();
514 fprintf(pFile, "scale %f %f %f\n",
515 pTrans->getScale()[0],
516 pTrans->getScale()[1],
517 pTrans->getScale()[2]);
519 pTrans->getScaleOrientation().getValueAsAxisRad(rQX, rQY, rQZ, rQW);
521 pWriter->printIndent();
522 fprintf(pFile, "scaleOrientation %f %f %f %f\n",
523 rQX, rQY, rQZ, rQW);
525 pWriter->printIndent();
526 fprintf(pFile, "translation %f %f %f\n",
527 pTrans->getTranslation()[0],
528 pTrans->getTranslation()[1],
529 pTrans->getTranslation()[2]);
531 pWriter->printIndent();
532 fprintf(pFile, "children [\n");
534 pWriter->incIndent(4);
537 return Action::Continue;
540 Action::ResultE VRMLWriteAction::writeComponentTransformLeave(NodeCore * const,
541 Action *pAction)
543 VRMLWriteAction *pWriter = dynamic_cast<VRMLWriteAction *>(pAction);
545 if(pWriter == NULL)
547 return Action::Quit;
550 FDEBUG(("Write ComponentTransform Leave 0x%04x\n", pWriter->getMode()));
552 if(pWriter->getMode() != VRMLWriteAction::OSGCollectFC)
554 FILE *pFile = pWriter->getFilePtr();
556 if(pFile == NULL)
558 return Action::Quit;
561 pWriter->decIndent(4);
563 pWriter->printIndent();
564 fprintf(pFile, "]\n");
566 pWriter->decIndent(4);
568 pWriter->printIndent();
569 fprintf(pFile, "}\n");
572 return Action::Continue;
575 Action::ResultE VRMLWriteAction::writeTransformEnter(NodeCore * const ,
576 Action *pAction)
578 VRMLWriteAction *pWriter = dynamic_cast<VRMLWriteAction *>(pAction);
579 Node *pNode = pAction->getActNode();
580 Transform *pTrans = dynamic_cast<Transform *>(pNode->getCore());
582 Real32 rQX;
583 Real32 rQY;
584 Real32 rQZ;
585 Real32 rQW;
587 if(pWriter == NULL)
589 return Action::Quit;
592 FDEBUG(("Write Transform Enter 0x%04x\n", pWriter->getMode()));
594 if(pWriter->getMode() == VRMLWriteAction::OSGCollectFC)
596 pWriter->addNodeUse(pNode);
598 else
600 FILE *pFile = pWriter->getFilePtr();
602 if(pFile == NULL)
604 return Action::Quit;
607 pWriter->updateProgress();
609 FCInfo *pInfo = pWriter->getInfo(pNode);
611 if(pInfo == NULL)
613 return Action::Quit;
616 if((pInfo->getName() != NULL ) &&
617 (pInfo->getWritten() == false) &&
618 (pInfo->getName()[0] != '\0'))
620 pWriter->printIndent();
621 fprintf(pFile, "DEF %s Transform\n", pInfo->getName());
623 pInfo->setWritten();
625 else
627 pWriter->printIndent();
628 fprintf(pFile, "Transform\n");
631 pWriter->printIndent();
632 fprintf(pFile, "{\n");
634 pWriter->incIndent(4);
636 // decompose matrix.
637 Matrix m = pTrans->getSFMatrix()->getValue();
638 Vec3f translation, scale, center;
639 Quaternion rotation, scaleOrientation;
640 m.getTransform(translation, rotation, scale, scaleOrientation);
642 pWriter->printIndent();
643 fprintf(pFile, "center %f %f %f\n",
644 center[0],
645 center[1],
646 center[2]);
648 rotation.getValueAsAxisRad(rQX, rQY, rQZ, rQW);
650 pWriter->printIndent();
651 fprintf(pFile, "rotation %f %f %f %f\n",
652 rQX, rQY, rQZ, rQW);
654 pWriter->printIndent();
655 fprintf(pFile, "scale %f %f %f\n",
656 scale[0],
657 scale[1],
658 scale[2]);
660 scaleOrientation.getValueAsAxisRad(rQX, rQY, rQZ, rQW);
662 pWriter->printIndent();
663 fprintf(pFile, "scaleOrientation %f %f %f %f\n",
664 rQX, rQY, rQZ, rQW);
666 pWriter->printIndent();
667 fprintf(pFile, "translation %f %f %f\n",
668 translation[0],
669 translation[1],
670 translation[2]);
672 pWriter->printIndent();
673 fprintf(pFile, "children [\n");
675 pWriter->incIndent(4);
678 return Action::Continue;
681 Action::ResultE VRMLWriteAction::writeTransformLeave(NodeCore * const ,
682 Action *pAction)
684 VRMLWriteAction *pWriter = dynamic_cast<VRMLWriteAction *>(pAction);
686 if(pWriter == NULL)
688 return Action::Quit;
691 FDEBUG(("Write Transform Leave 0x%04x\n", pWriter->getMode()));
693 if(pWriter->getMode() != VRMLWriteAction::OSGCollectFC)
695 FILE *pFile = pWriter->getFilePtr();
697 if(pFile == NULL)
699 return Action::Quit;
702 pWriter->decIndent(4);
704 pWriter->printIndent();
705 fprintf(pFile, "]\n");
707 pWriter->decIndent(4);
709 pWriter->printIndent();
710 fprintf(pFile, "}\n");
713 return Action::Continue;
716 void VRMLWriteAction::writePoints(Geometry *pGeo,
717 FILE *pFile,
718 VRMLWriteAction *pWriter)
720 if(pGeo == NULL)
721 return;
723 GeoVectorProperty *pPos = pGeo->getPositions();
725 if(pPos == NULL)
726 return;
728 pWriter->printIndent();
729 fprintf(pFile, "coord Coordinate\n");
731 pWriter->printIndent();
732 fprintf(pFile, "{\n");
733 pWriter->incIndent(4);
735 pWriter->printIndent();
736 fprintf(pFile, "point [\n");
737 pWriter->incIndent(4);
739 for(UInt32 i = 0; i < pPos->size32(); i++)
741 pWriter->printIndent();
743 Pnt3f p;
744 pPos->getValue(p,i);
746 fprintf(pFile, "%f %f %f", p[0], p[1], p[2]);
748 if(i == pPos->size() - 1)
750 fprintf(pFile, "\n");
752 else
754 fprintf(pFile, ", \n");
758 pWriter->decIndent(4);
759 pWriter->printIndent();
760 fprintf(pFile, "]\n");
762 pWriter->decIndent(4);
763 pWriter->printIndent();
764 fprintf(pFile, "}\n");
768 void VRMLWriteAction::writePointSetPoints(Geometry *pGeo,
769 FILE *pFile,
770 VRMLWriteAction *pWriter)
772 if(pGeo == NULL)
773 return;
775 GeoVectorProperty *pPos = pGeo->getPositions();
777 if(pPos == NULL)
778 return;
780 pWriter->printIndent();
781 fprintf(pFile, "coord Coordinate\n");
783 pWriter->printIndent();
784 fprintf(pFile, "{\n");
785 pWriter->incIndent(4);
787 pWriter->printIndent();
788 fprintf(pFile, "point [\n");
789 pWriter->incIndent(4);
791 PointIterator it;
792 UInt32 i;
794 for(i = 0, it = pGeo->beginPoints(); it != pGeo->endPoints(); ++it, ++i)
796 pWriter->printIndent();
798 Pnt3f p = it.getPosition(0);
800 fprintf(pFile, "%f %f %f", p[0], p[1], p[2]);
802 if(i == pPos->size() - 1)
804 fprintf(pFile, "\n");
806 else
808 fprintf(pFile, ", \n");
812 pWriter->decIndent(4);
813 pWriter->printIndent();
814 fprintf(pFile, "]\n");
816 pWriter->decIndent(4);
817 pWriter->printIndent();
818 fprintf(pFile, "}\n");
823 void VRMLWriteAction::writeNormals(Geometry *pGeo,
824 FILE *pFile,
825 VRMLWriteAction *pWriter)
827 if(0 != (pWriter->getOptions() & VRMLWriteAction::OSGNoNormals))
828 return;
830 if(pGeo == NULL)
831 return;
833 GeoVectorProperty *pNorm = pGeo->getNormals();
835 if(pNorm == NULL)
836 return;
838 pWriter->printIndent();
839 fprintf(pFile, "normal Normal\n");
841 pWriter->printIndent();
842 fprintf(pFile, "{\n");
843 pWriter->incIndent(4);
845 pWriter->printIndent();
846 fprintf(pFile, "vector [\n");
847 pWriter->incIndent(4);
849 for(UInt32 i = 0; i < pNorm->size32(); i++)
851 pWriter->printIndent();
853 Vec3f n;
854 pNorm->getValue(n,i);
856 fprintf(pFile, "%f %f %f", n[0], n[1], n[2]);
858 if(i == pNorm->size() - 1)
860 fprintf(pFile, "\n");
862 else
864 fprintf(pFile, ", \n");
868 pWriter->decIndent(4);
869 pWriter->printIndent();
870 fprintf(pFile, "]\n");
872 pWriter->decIndent(4);
873 pWriter->printIndent();
874 fprintf(pFile, "}\n");
877 void VRMLWriteAction::writeColors(Geometry *pGeo,
878 FILE *pFile,
879 VRMLWriteAction *pWriter)
881 if(pGeo == NULL)
882 return;
884 GeoVectorProperty *pCol = pGeo->getColors();
886 if(pCol == NULL)
887 return;
889 pWriter->printIndent();
890 fprintf(pFile, "color Color\n");
892 pWriter->printIndent();
893 fprintf(pFile, "{\n");
894 pWriter->incIndent(4);
896 pWriter->printIndent();
897 fprintf(pFile, "color [\n");
898 pWriter->incIndent(4);
900 for(UInt32 i = 0; i < pCol->size32(); i++)
902 pWriter->printIndent();
904 Color3f c;
905 pCol->getValue(c,i);
907 fprintf(pFile, "%f %f %f", c[0], c[1], c[2]);
909 if(i == pCol->size() - 1)
911 fprintf(pFile, "\n");
913 else
915 fprintf(pFile, ", \n");
919 pWriter->decIndent(4);
920 pWriter->printIndent();
921 fprintf(pFile, "]\n");
923 pWriter->decIndent(4);
924 pWriter->printIndent();
925 fprintf(pFile, "}\n");
928 void VRMLWriteAction::writePointSetColors(Geometry *pGeo,
929 FILE *pFile,
930 VRMLWriteAction *pWriter)
932 if(pGeo == NULL)
933 return;
935 GeoVectorProperty *pCol = pGeo->getColors();
937 if(pCol == NULL)
938 return;
940 pWriter->printIndent();
941 fprintf(pFile, "color Color\n");
943 pWriter->printIndent();
944 fprintf(pFile, "{\n");
945 pWriter->incIndent(4);
947 pWriter->printIndent();
948 fprintf(pFile, "color [\n");
949 pWriter->incIndent(4);
951 PointIterator it;
952 UInt32 i;
954 for(i = 0, it = pGeo->beginPoints(); it != pGeo->endPoints(); ++it, ++i)
956 pWriter->printIndent();
958 Color3f c = it.getColor(0);
960 fprintf(pFile, "%f %f %f", c[0], c[1], c[2]);
962 if(i == pCol->size() - 1)
964 fprintf(pFile, "\n");
966 else
968 fprintf(pFile, ", \n");
972 pWriter->decIndent(4);
973 pWriter->printIndent();
974 fprintf(pFile, "]\n");
976 pWriter->decIndent(4);
977 pWriter->printIndent();
978 fprintf(pFile, "}\n");
982 void VRMLWriteAction::writeTexCoords(Geometry *pGeo,
983 FILE *pFile,
984 VRMLWriteAction *pWriter)
986 if(pGeo == NULL)
987 return;
989 GeoVectorProperty *pTex = pGeo->getTexCoords();
991 if(pTex == NULL)
992 return;
994 pWriter->printIndent();
995 fprintf(pFile, "texCoord TextureCoordinate\n");
997 pWriter->printIndent();
998 fprintf(pFile, "{\n");
999 pWriter->incIndent(4);
1001 pWriter->printIndent();
1002 fprintf(pFile, "point [\n");
1003 pWriter->incIndent(4);
1005 for(UInt32 i = 0; i < pTex->size32(); i++)
1007 pWriter->printIndent();
1009 Vec2f t;
1010 pTex->getValue(t,i);
1012 fprintf(pFile, "%f %f", t[0], t[1]);
1014 if(i == pTex->size() - 1)
1016 fprintf(pFile, "\n");
1018 else
1020 fprintf(pFile, ", \n");
1024 pWriter->decIndent(4);
1025 pWriter->printIndent();
1026 fprintf(pFile, "]\n");
1028 pWriter->decIndent(4);
1029 pWriter->printIndent();
1030 fprintf(pFile, "}\n");
1033 void VRMLWriteAction::writeIndex(Geometry *pGeo,
1034 FILE *pFile,
1035 VRMLWriteAction *pWriter)
1037 if(pGeo == NULL)
1038 return;
1040 GeoIntegralProperty *pTypes = pGeo->getTypes ();
1041 GeoIntegralProperty *pLength = pGeo->getLengths();
1043 if((pTypes == NULL) ||
1044 (pLength == NULL))
1046 return;
1049 if(pTypes ->size() == 0 ||
1050 pLength->size() == 0)
1052 return;
1055 pWriter->printIndent();
1056 fprintf(pFile, "coordIndex [\n");
1057 pWriter->incIndent(4);
1059 TriangleIterator it;
1061 for(it = pGeo->beginTriangles(); it != pGeo->endTriangles(); ++it)
1063 pWriter->printIndent();
1065 for(UInt32 i = 0; i < 3; ++i)
1067 fprintf(pFile, "%d, ", it.getPositionIndex(i));
1070 fprintf(pFile, "%d,%d,%d,", it.getPositionIndex(0),
1071 it.getPositionIndex(1),
1072 it.getPositionIndex(2));
1073 if(it.getPositionIndex(3) != -1)
1074 fprintf(pFile, "%d,", it.getPositionIndex(3));
1077 fprintf(pFile, "-1,\n");
1080 pWriter->decIndent(4);
1081 pWriter->printIndent();
1082 fprintf(pFile, "]\n");
1084 if(pGeo->getNormals() != NULL &&
1085 pGeo->getNormals()->size() > 0 &&
1086 0 == (pWriter->getOptions() & VRMLWriteAction::OSGNoNormals))
1088 pWriter->printIndent();
1089 fprintf(pFile, "normalIndex [\n");
1090 pWriter->incIndent(4);
1092 for(it = pGeo->beginTriangles(); it != pGeo->endTriangles(); ++it)
1094 pWriter->printIndent();
1096 for(UInt32 i = 0; i < 3; ++i)
1098 fprintf(pFile, "%d, ", it.getNormalIndex(i));
1102 fprintf(pFile, "%d,%d,%d,", it.getNormalIndex(0),
1103 it.getNormalIndex(1),
1104 it.getNormalIndex(2));
1105 if(it.getNormalIndex(3) != -1)
1106 fprintf(pFile, "%d,", it.getNormalIndex(3));
1109 fprintf(pFile, "-1,\n");
1112 pWriter->decIndent(4);
1113 pWriter->printIndent();
1114 fprintf(pFile, "]\n");
1117 if(pGeo->getColors() != NULL && pGeo->getColors()->size() > 0)
1119 pWriter->printIndent();
1120 fprintf(pFile, "colorIndex [\n");
1121 pWriter->incIndent(4);
1123 for(it = pGeo->beginTriangles(); it != pGeo->endTriangles(); ++it)
1125 pWriter->printIndent();
1127 for(UInt32 i = 0; i < 3; ++i)
1129 fprintf(pFile, " %d,", it.getColorIndex(i));
1132 fprintf(pFile, "%d,%d,%d,", it.getColorIndex(0),
1133 it.getColorIndex(1),
1134 it.getColorIndex(2));
1135 if(it.getColorIndex(3) != -1)
1136 fprintf(pFile, "%d,", it.getColorIndex(3));
1139 fprintf(pFile, "-1,\n");
1142 pWriter->decIndent(4);
1143 pWriter->printIndent();
1144 fprintf(pFile, "]\n");
1147 if(pGeo->getTexCoords() != NULL && pGeo->getTexCoords()->size() > 0)
1149 pWriter->printIndent();
1150 fprintf(pFile, "texCoordIndex [\n");
1151 pWriter->incIndent(4);
1153 for(it = pGeo->beginTriangles(); it != pGeo->endTriangles(); ++it)
1155 pWriter->printIndent();
1157 for(UInt32 i = 0; i < 3; ++i)
1159 fprintf(pFile, "%d,", it.getTexCoordsIndex(i));
1162 fprintf(pFile, "%d,%d,%d,", it.getTexCoordsIndex(0),
1163 it.getTexCoordsIndex(1),
1164 it.getTexCoordsIndex(2));
1165 if(it.getTexCoordsIndex(3) != -1)
1166 fprintf(pFile, "%d,", it.getTexCoordsIndex(3));
1169 fprintf(pFile, "-1,\n");
1172 pWriter->decIndent(4);
1173 pWriter->printIndent();
1174 fprintf(pFile, "]\n");
1178 void VRMLWriteAction::writeLineIndex(Geometry *pGeo,
1179 FILE *pFile,
1180 VRMLWriteAction *pWriter)
1182 if(pGeo == NULL)
1183 return;
1185 GeoIntegralProperty *pTypes = pGeo->getTypes();
1186 GeoIntegralProperty *pLength = pGeo->getLengths();
1188 if((pTypes == NULL) ||
1189 (pLength == NULL))
1191 return;
1194 if(pTypes->size() == 0 ||
1195 pLength->size() == 0)
1197 return;
1200 pWriter->printIndent();
1201 fprintf(pFile, "coordIndex [\n");
1202 pWriter->incIndent(4);
1204 PrimitiveIterator it;
1205 UInt32 i;
1207 for(it = pGeo->beginPrimitives(); it != pGeo->endPrimitives(); ++it)
1209 if(it.getType() == GL_LINES)
1211 for(i = 0; i < it.getLength(); i += 2)
1213 pWriter->printIndent();
1215 fprintf(pFile, "%d, %d, -1,\n",
1216 it.getPositionIndex(i),
1217 it.getPositionIndex(i + 1));
1220 else if(it.getType() == GL_LINE_STRIP)
1222 pWriter->printIndent();
1224 for(i = 0; i < it.getLength(); ++i)
1226 fprintf(pFile, "%d, ", it.getPositionIndex(i));
1229 fprintf(pFile, "-1,\n");
1231 else if(it.getType() == GL_LINE_LOOP)
1233 pWriter->printIndent();
1235 for(i = 0; i < it.getLength(); ++i)
1237 fprintf(pFile, "%d, ", it.getPositionIndex(i));
1240 fprintf(pFile, "%d, -1, \n", it.getPositionIndex(i - 1));
1244 pWriter->decIndent(4);
1245 pWriter->printIndent();
1246 fprintf(pFile, "]\n");
1249 if(pGeo->getColors() != NULL && pGeo->getColors()->size() > 0)
1251 pWriter->printIndent();
1252 fprintf(pFile, "colorIndex [\n");
1253 pWriter->incIndent(4);
1255 for(it = pGeo->beginPrimitives(); it != pGeo->endPrimitives(); ++it)
1257 if(it.getType() == GL_LINES)
1259 for(i = 0; i < it.getLength(); i += 2)
1261 pWriter->printIndent();
1263 fprintf(pFile, "%d, %d, -1,\n",
1264 it.getColorIndex(i),
1265 it.getColorIndex(i + 1));
1268 else if(it.getType() == GL_LINE_STRIP)
1270 pWriter->printIndent();
1272 for(i = 0; i < it.getLength(); ++i)
1274 fprintf(pFile, "%d, ", it.getColorIndex(i));
1277 fprintf(pFile, "-1,\n");
1279 else if(it.getType() == GL_LINE_LOOP)
1281 pWriter->printIndent();
1283 for(i = 0; i < it.getLength(); ++i)
1285 fprintf(pFile, "%d, ", it.getColorIndex(i));
1288 fprintf(pFile, "%d, -1, \n", it.getColorIndex(i - 1));
1292 pWriter->decIndent(4);
1293 pWriter->printIndent();
1294 fprintf(pFile, "]\n");
1298 void VRMLWriteAction::writeMaterial(Geometry *pGeo,
1299 FILE *pFile,
1300 VRMLWriteAction *pWriter)
1302 if(pGeo == NULL)
1303 return;
1305 Material *pMat;
1307 pMat = pWriter->getMaterial();
1309 if(pMat == NULL)
1310 pMat = pGeo->getMaterial();
1312 if(pMat == NULL)
1313 pMat = OSG::getDefaultMaterial();
1315 if(pWriter->isWritten(pMat))
1317 pWriter->printIndent();
1318 fprintf(pFile, "appearance USE App_%u\n", pWriter->getIndex(pMat));
1319 return;
1322 PrimeMaterial *pPrimeMat = pMat->finalize(0x0000, NULL, NULL);
1324 pPrimeMat->rebuildState();
1325 State *st = pPrimeMat->getState();
1327 StateChunk *sChunk =
1328 st->getChunk(MaterialChunk::getStaticClassId());
1330 if(sChunk == NULL)
1331 return;
1333 MaterialChunk *mChunk = dynamic_cast<MaterialChunk *>(sChunk);
1335 if(mChunk == NULL)
1336 return;
1338 pWriter->printIndent();
1339 fprintf(pFile, "appearance DEF App_%u Appearance\n",
1340 pWriter->setWritten(pMat));
1342 pWriter->printIndent();
1343 fprintf(pFile, "{\n");
1345 pWriter->incIndent(4);
1347 pWriter->printIndent();
1348 fprintf(pFile, "material Material\n");
1350 pWriter->printIndent();
1351 fprintf(pFile, "{\n");
1353 pWriter->incIndent(4);
1355 Real32 rAmbient = 0.f;
1357 if(osgAbs(mChunk->getDiffuse()[0]) > TypeTraits<Real32>::getDefaultEps())
1359 rAmbient = mChunk->getAmbient()[0] / mChunk->getDiffuse()[0];
1361 else if(osgAbs(mChunk->getDiffuse()[1]) > TypeTraits<Real32>::getDefaultEps())
1363 rAmbient = mChunk->getAmbient()[1] / mChunk->getDiffuse()[1];
1365 else if(osgAbs(mChunk->getDiffuse()[2]) > TypeTraits<Real32>::getDefaultEps())
1367 rAmbient = mChunk->getAmbient()[2] / mChunk->getDiffuse()[2];
1371 pWriter->printIndent();
1372 fprintf(pFile, "ambientIntensity %f\n", rAmbient);
1374 pWriter->printIndent();
1375 fprintf(pFile, "diffuseColor %f %f %f\n",
1376 mChunk->getDiffuse()[0],
1377 mChunk->getDiffuse()[1],
1378 mChunk->getDiffuse()[2]);
1380 pWriter->printIndent();
1381 if(!mChunk->getLit())
1383 fprintf(pFile, "emissiveColor 1.0 1.0 1.0\n");
1385 else
1387 fprintf(pFile, "emissiveColor %f %f %f\n",
1388 mChunk->getEmission()[0],
1389 mChunk->getEmission()[1],
1390 mChunk->getEmission()[2]);
1393 pWriter->printIndent();
1394 fprintf(pFile, "shininess %f\n",
1395 mChunk->getShininess() / 128.);
1397 pWriter->printIndent();
1398 fprintf(pFile, "specularColor %f %f %f\n",
1399 mChunk->getSpecular()[0],
1400 mChunk->getSpecular()[1],
1401 mChunk->getSpecular()[2]);
1403 pWriter->printIndent();
1404 fprintf(pFile, "transparency %f\n",
1405 1.f-mChunk->getDiffuse()[3]);
1407 pWriter->decIndent(4);
1409 pWriter->printIndent();
1410 fprintf(pFile, "}\n");
1412 sChunk = st->getChunk(TextureObjChunk::getStaticClassId());
1414 TextureObjChunk *pTChunk = dynamic_cast<TextureObjChunk *>(sChunk);
1416 if(pTChunk != NULL)
1418 if(pWriter->isWritten(pTChunk))
1420 pWriter->printIndent();
1421 fprintf(pFile, "texture USE Tex_%u\n", pWriter->getIndex(pTChunk));
1423 else
1425 Image *pImage = pTChunk->getImage();
1427 if(pImage != NULL)
1429 if(pWriter->getOptions() &
1430 VRMLWriteAction::OSGPixelTextures)
1432 pWriter->printIndent();
1433 fprintf(pFile, "texture DEF Tex_%u PixelTexture\n",
1434 pWriter->setWritten(pTChunk) );
1436 pWriter->printIndent();
1437 fprintf(pFile, "{\n");
1439 pWriter->incIndent(4);
1441 UInt32 pixelformat = pImage->getPixelFormat();
1442 UInt32 pixelsize = 1;
1443 if ( pixelformat == Image::OSG_RGB_PF)
1444 pixelsize = 3;
1445 else if ( pixelformat == Image::OSG_RGBA_PF)
1446 pixelsize = 4;
1447 else if ( pixelformat == Image::OSG_LA_PF )
1448 pixelsize = 2;
1450 pWriter->printIndent();
1451 fprintf(pFile, "image %d %d %u ",
1452 pImage->getWidth(), pImage->getHeight(), pixelsize);
1454 const UInt8 *data = pImage->getData();
1455 for (Int32 x=0; x<pImage->getHeight(); ++x)
1457 for (Int32 y=0; y<pImage->getWidth(); ++y)
1459 UInt32 pos = (x * pImage->getWidth() + y) * pixelsize;
1460 fprintf(pFile, "0x");
1461 for (UInt32 i=0;i<pixelsize;i++)
1463 fprintf(pFile, "%02X", data[pos+i] );
1465 fprintf(pFile, " ");
1467 fprintf(pFile, "\n");
1470 if(pTChunk->getWrapS() != GL_REPEAT)
1472 pWriter->printIndent();
1473 fprintf(pFile, "repeatS FALSE\n");
1476 if(pTChunk->getWrapT() != GL_REPEAT)
1478 pWriter->printIndent();
1479 fprintf(pFile, "repeatT FALSE\n");
1482 pWriter->decIndent(4);
1484 pWriter->printIndent();
1485 fprintf(pFile, "}\n");
1487 else
1489 const std::string *pFilename =
1490 pImage->findAttachmentField("fileName");
1491 std::string filename;
1492 if(pFilename == NULL)
1493 filename = pImage->getName();
1494 else
1495 filename = *pFilename;
1497 if(!filename.empty())
1500 pWriter->printIndent();
1501 fprintf(pFile, "texture DEF Tex_%u ImageTexture\n",
1502 pWriter->setWritten(pTChunk) );
1504 pWriter->printIndent();
1505 fprintf(pFile, "{\n");
1507 pWriter->incIndent(4);
1509 pWriter->printIndent();
1510 fprintf(pFile, "url \"%s\"\n",
1511 filename.c_str());
1513 if(pTChunk->getWrapS() != GL_REPEAT)
1515 pWriter->printIndent();
1516 fprintf(pFile, "repeatS FALSE\n");
1519 if(pTChunk->getWrapT() != GL_REPEAT)
1521 pWriter->printIndent();
1522 fprintf(pFile, "repeatT FALSE\n");
1525 pWriter->decIndent(4);
1527 pWriter->printIndent();
1528 fprintf(pFile, "}\n");
1535 sChunk = st->getChunk(TextureTransformChunk::getStaticClassId());
1537 TextureTransformChunkPtr pTTChunk = dynamic_cast<TextureTransformChunkPtr>(sChunk);
1539 if(pTTChunk != NULL)
1544 pWriter->decIndent(4);
1546 pWriter->printIndent();
1547 fprintf(pFile, "}\n");
1550 bool VRMLWriteAction::writeGeoCommon(Node *pNode,
1551 Geometry *pGeo,
1552 FILE *pFile,
1553 VRMLWriteAction *pWriter,
1554 const Char8 *setTypename)
1556 FCInfo *pInfo = pWriter->getInfo(pNode);
1557 FCInfo *pCoreInfo = pWriter->getInfo(pGeo);
1559 if(pInfo == NULL || pCoreInfo == NULL || setTypename == NULL)
1561 FWARNING(("Info missing %p %p\n",
1562 static_cast<void *>(pInfo),
1563 static_cast<void *>(pCoreInfo)));
1564 return false;
1567 if(pCoreInfo->getUse() > 0 &&
1568 pCoreInfo->getWritten() == true)
1570 pWriter->printIndent();
1571 fprintf(pFile, "geometry USE %s\n", pCoreInfo->getName());
1572 pWriter->setCurrentUse(true);
1574 else
1576 if((pCoreInfo->getName() != NULL) &&
1577 (pCoreInfo->getName()[0] != '\0'))
1579 pWriter->printIndent();
1580 fprintf(pFile, "geometry DEF %s %s\n",
1581 pCoreInfo->getName(),
1582 setTypename);
1584 pCoreInfo->setWritten();
1586 else if((pInfo->getName() != NULL) &&
1587 (pInfo->getName()[0] != '\0'))
1589 pWriter->printIndent();
1590 fprintf(pFile,
1591 "geometry DEF %s %s\n",
1592 pInfo->getName(),
1593 setTypename);
1595 pInfo->setWritten();
1597 else
1599 pWriter->printIndent();
1600 fprintf(pFile, "geometry %s\n", setTypename);
1604 pWriter->printIndent();
1605 fprintf(pFile, "{\n");
1607 pWriter->incIndent(4);
1610 return true;
1611 #if 0
1613 // pWriter->printIndent();
1614 // !!! fprintf(pFile, "colorPerVertex %s\n",
1615 // !!! pGeo->getColorPerVertex() ? "TRUE" : "FALSE");
1617 // pWriter->printIndent();
1618 // !!! fprintf(pFile, "normalPerVertex %s\n",
1619 // !!! pGeo->getNormalPerVertex() ? "TRUE" : "FALSE");
1620 #endif
1623 void VRMLWriteAction::writePointSet(Node *pNode,
1624 Geometry *pGeo,
1625 FILE *pFile,
1626 VRMLWriteAction *pWriter)
1628 if(writeGeoCommon(pNode, pGeo, pFile, pWriter, "PointSet") == true)
1630 if(pWriter->isCurrentUse() == false)
1632 writePointSetPoints(pGeo, pFile, pWriter);
1633 writePointSetColors(pGeo, pFile, pWriter);
1635 pWriter->decIndent(4);
1637 pWriter->printIndent();
1638 fprintf(pFile, "}\n");
1641 pWriter->setCurrentUse(false);
1645 void VRMLWriteAction::writeLineSet(Node *pNode,
1646 Geometry *pGeo,
1647 FILE *pFile,
1648 VRMLWriteAction *pWriter,
1649 bool )
1651 if(writeGeoCommon(pNode, pGeo, pFile, pWriter, "IndexedLineSet") == true)
1654 if(pWriter->isCurrentUse() == false)
1656 writePoints (pGeo, pFile, pWriter);
1657 writeColors (pGeo, pFile, pWriter);
1659 writeLineIndex(pGeo, pFile, pWriter);
1661 pWriter->decIndent(4);
1663 pWriter->printIndent();
1664 fprintf(pFile, "}\n");
1666 writeMaterial(pGeo, pFile, pWriter);
1669 pWriter->setCurrentUse(false);
1673 void VRMLWriteAction::writeFaceSet(Node *pNode,
1674 Geometry *pGeo,
1675 FILE *pFile,
1676 VRMLWriteAction *pWriter,
1677 bool )
1679 if(writeGeoCommon(pNode, pGeo, pFile, pWriter, "IndexedFaceSet") == true)
1681 if(pWriter->isCurrentUse() == false)
1683 pWriter->printIndent();
1684 fprintf(pFile, "solid FALSE\n");
1686 writePoints (pGeo, pFile, pWriter);
1687 writeNormals (pGeo, pFile, pWriter);
1688 writeColors (pGeo, pFile, pWriter);
1689 writeTexCoords(pGeo, pFile, pWriter);
1691 writeIndex (pGeo, pFile, pWriter);
1693 pWriter->decIndent(4);
1695 pWriter->printIndent();
1696 fprintf(pFile, "}\n");
1698 writeMaterial(pGeo, pFile, pWriter);
1701 pWriter->setCurrentUse(false);
1706 Action::ResultE VRMLWriteAction::writeGeoEnter(NodeCore * const ,
1707 Action *pAction)
1709 VRMLWriteAction *pWriter = dynamic_cast<VRMLWriteAction *>(pAction);
1711 Node *pNode = pAction->getActNode();
1712 Geometry *pGeo = dynamic_cast<Geometry *>(pNode->getCore());
1714 if(pWriter == NULL || pGeo == NULL)
1716 return Action::Quit;
1719 FDEBUG(("Write Geo Enter 0x%04x\n", pWriter->getMode()));
1721 if(pWriter->getMode() == VRMLWriteAction::OSGCollectFC)
1723 pWriter->addNodeUse(pNode);
1725 pWriter->addContainerUse(pGeo->getPositions());
1726 pWriter->addContainerUse(pGeo->getNormals ());
1727 pWriter->addContainerUse(pGeo->getColors ());
1728 pWriter->addContainerUse(pGeo->getTexCoords());
1730 else
1732 FILE *pFile = pWriter->getFilePtr();
1734 if(pFile == NULL)
1736 return Action::Quit;
1739 pWriter->updateProgress();
1741 pWriter->printIndent();
1742 fprintf(pFile, "Shape\n");
1743 pWriter->printIndent();
1744 fprintf(pFile, "{\n");
1746 pWriter->incIndent(4);
1748 PrimitiveIterator pIt = pGeo->beginPrimitives();
1749 PrimitiveIterator pEnd = pGeo->endPrimitives();
1751 UInt32 uiPointCount = 0;
1752 UInt32 uiLineCount = 0;
1753 UInt32 uiFaceCount = 0;
1755 while(pIt != pEnd)
1757 if(pIt.getType() == GL_LINES ||
1758 pIt.getType() == GL_LINE_STRIP ||
1759 pIt.getType() == GL_LINE_LOOP )
1761 ++uiLineCount;
1763 else if(pIt.getType() == GL_POINTS)
1765 ++uiPointCount;
1767 else
1769 ++uiFaceCount;
1772 ++pIt;
1775 FINFO(( "Geo Stat : %d %d %d\n",
1776 uiPointCount,
1777 uiLineCount,
1778 uiFaceCount));
1780 if(uiPointCount != 0)
1782 if((uiLineCount != 0) || (uiFaceCount != 0))
1784 FWARNING(("ERROR writer does not support mixed primitives"
1785 "including points\n"));
1787 else
1789 writePointSet(pNode, pGeo, pFile, pWriter);
1793 if(uiLineCount != 0)
1795 writeLineSet(pNode,
1796 pGeo,
1797 pFile,
1798 pWriter,
1799 ((uiPointCount == 0) && (uiFaceCount == 0)));
1802 if(uiFaceCount != 0)
1804 writeFaceSet(pNode,
1805 pGeo,
1806 pFile,
1807 pWriter,
1808 ((uiPointCount == 0) && (uiLineCount == 0)));
1812 return Action::Continue;
1815 Action::ResultE VRMLWriteAction::writeGeoLeave(NodeCore * const ,
1816 Action *pAction)
1818 VRMLWriteAction *pWriter = dynamic_cast<VRMLWriteAction *>(pAction);
1820 if(pWriter == NULL)
1822 return Action::Quit;
1825 FDEBUG(("Write Geo Leave 0x%04x\n", pWriter->getMode()));
1827 if(pWriter->getMode() != VRMLWriteAction::OSGCollectFC)
1829 FILE *pFile = pWriter->getFilePtr();
1831 if(pFile == NULL)
1833 return Action::Quit;
1836 pWriter->decIndent(4);
1838 pWriter->printIndent();
1839 fprintf(pFile, "}\n");
1842 return Action::Continue;
1845 Action::ResultE VRMLWriteAction::writeMatGroupEnter(NodeCore * const ,
1846 Action *pAction)
1848 VRMLWriteAction *pWriter = dynamic_cast<VRMLWriteAction *>(pAction);
1850 Node *pNode = pAction->getActNode();
1852 MaterialGroup *pMatGroup =
1853 dynamic_cast<MaterialGroup *>(pNode->getCore());
1855 if(pWriter == NULL || pMatGroup == NULL)
1857 return Action::Quit;
1860 FDEBUG(("Write MatGroup Enter 0x%04x\n", pWriter->getMode()));
1862 pWriter->setMaterial(pMatGroup->getMaterial());
1864 return Action::Continue;
1867 Action::ResultE VRMLWriteAction::writeMatGroupLeave(NodeCore * const ,
1868 Action *pAction)
1870 VRMLWriteAction *pWriter = dynamic_cast<VRMLWriteAction *>(pAction);
1873 if(pWriter == NULL)
1875 return Action::Quit;
1878 FDEBUG(("Write MatGroup Leave 0x%04x\n", pWriter->getMode()));
1880 pWriter->setMaterial(NULL);
1882 return Action::Continue;
1886 bool VRMLWriteAction::initializeAction(void)
1888 FINFO(( "Init VRMLWriter\n" ));
1890 VRMLWriteAction::registerEnterDefault(
1891 Group::getClassType(), &VRMLWriteAction::writeGroupEnter);
1893 VRMLWriteAction::registerEnterDefault(
1894 ComponentTransform::getClassType(),
1895 &VRMLWriteAction::writeComponentTransformEnter);
1897 VRMLWriteAction::registerEnterDefault(
1898 Transform::getClassType(), &VRMLWriteAction::writeTransformEnter);
1900 VRMLWriteAction::registerEnterDefault(
1901 Geometry::getClassType(), &VRMLWriteAction::writeGeoEnter);
1903 VRMLWriteAction::registerEnterDefault(
1904 MaterialGroup::getClassType(), &VRMLWriteAction::writeMatGroupEnter);
1907 VRMLWriteAction::registerLeaveDefault(
1908 Group::getClassType(), &VRMLWriteAction::writeGroupLeave);
1910 VRMLWriteAction::registerLeaveDefault(
1911 ComponentTransform::getClassType(),
1912 &VRMLWriteAction::writeComponentTransformLeave);
1914 VRMLWriteAction::registerLeaveDefault(
1915 Transform::getClassType(), &VRMLWriteAction::writeTransformLeave);
1917 VRMLWriteAction::registerLeaveDefault(
1918 Geometry::getClassType(), &VRMLWriteAction::writeGeoLeave);
1920 VRMLWriteAction::registerLeaveDefault(
1921 MaterialGroup::getClassType(), &VRMLWriteAction::writeMatGroupLeave);
1923 return true;
1926 bool VRMLWriteAction::terminateAction(void)
1928 FINFO(( "Terminate VRMLWriter\n" ));
1930 delete _defaultEnterFunctors;
1931 delete _defaultLeaveFunctors;
1933 return true;
1937 void VRMLWriteAction::incIndent(UInt32 uiDelta)
1939 if(0 == (_uiOptions & OSGNoIndent))
1941 _uiIndent += uiDelta;
1945 void VRMLWriteAction::decIndent(UInt32 uiDelta)
1947 if(0 == (_uiOptions & OSGNoIndent))
1949 _uiIndent -= uiDelta;
1953 void VRMLWriteAction::printIndent(void)
1955 if(_pFile != NULL)
1957 for(UInt32 i = 0; i < _uiIndent/8; i++)
1959 fprintf(_pFile, "\t");
1961 for(UInt32 i = 0; i < _uiIndent%8; i++)
1963 fprintf(_pFile, " ");
1968 void VRMLWriteAction::setCurrentUse(bool bVal)
1970 _currentUse = bVal;
1973 bool VRMLWriteAction::isCurrentUse(void)
1975 return _currentUse;
1978 void VRMLWriteAction::addNodeUse(Node * pNode)
1980 if(pNode == NULL)
1981 return;
1983 NodeCore *pCore = pNode->getCore();
1985 if(_vFCInfos.find(pNode->getId()) == _vFCInfos.end())
1986 _vFCInfos.insert(std::make_pair(pNode->getId(), new FCInfo));
1988 if(_vFCInfos.find(pCore->getId()) == _vFCInfos.end())
1989 _vFCInfos.insert(std::make_pair(pCore->getId(), new FCInfo));
1991 FCInfo *pInfoNode = _vFCInfos[pNode->getId()];
1992 FCInfo *pInfoCore = _vFCInfos[pCore->getId()];
1994 Name *pNodename =
1995 dynamic_cast<Name *>(pNode->findAttachment(
1996 Name::getClassType().getGroupId()));
1998 Name *pCorename =
1999 dynamic_cast<Name *>(pCore->findAttachment(
2000 Name::getClassType().getGroupId()));
2002 pInfoNode->incUse();
2003 pInfoCore->incUse();
2005 if(pNodename != NULL)
2007 pInfoNode->setName(pNodename->getFieldPtr()->getValue().c_str());
2010 if(pCorename != NULL)
2012 pInfoCore->setName(pCorename->getFieldPtr()->getValue().c_str());
2015 if(pInfoCore->getUse() > 1)
2017 if(pCorename != NULL)
2019 pInfoCore->buildName(pCore->getTypeName(),
2020 pCore->getId());
2024 ++_nodeCount;
2027 void VRMLWriteAction::addContainerUse(FieldContainer *pContainer)
2029 if(pContainer == NULL)
2030 return;
2032 if(_vFCInfos.find(pContainer->getId()) == _vFCInfos.end())
2033 _vFCInfos.insert(std::make_pair(pContainer->getId(), new FCInfo));
2035 FCInfo *pInfo = _vFCInfos[pContainer->getId()];
2037 pInfo->incUse();
2039 if(pInfo->getUse() > 1)
2041 pInfo->buildName(pContainer->getTypeName(),
2042 pContainer->getId());
2046 void VRMLWriteAction::clearInfos(void)
2048 for(FCInfosMap::iterator it = _vFCInfos.begin();it != _vFCInfos.end();++it)
2049 delete (*it).second;
2050 _vFCInfos.clear();
2053 VRMLWriteAction::FCInfo *VRMLWriteAction::getInfo(
2054 FieldContainer *pContainer)
2056 if(pContainer == NULL)
2057 return NULL;
2059 if(_vFCInfos.find(pContainer->getId()) == _vFCInfos.end())
2060 return NULL;
2062 return _vFCInfos[pContainer->getId()];
2065 void VRMLWriteAction::updateProgress(void)
2067 if(_nodeCount > 0)
2068 SceneFileHandler::the()->updateWriteProgress((_currentNodeCount++ * 100) / _nodeCount);
2071 /***************************************************************************\
2072 * Instance methods *
2073 \***************************************************************************/
2075 /*-------------------------------------------------------------------------*\
2076 - public -
2077 \*-------------------------------------------------------------------------*/
2079 /*------------- constructors & destructors --------------------------------*/
2081 /** \brief Constructor
2084 VRMLWriteAction::VRMLWriteAction(void) :
2085 Inherited ( ),
2086 _material (NULL ),
2087 _uiIndent (0 ),
2088 _pFile (NULL ),
2089 _eTraversalMode (OSGCollectFC),
2090 _currentUse (false ),
2091 _uiOptions (OSGNoOptions),
2092 _vFCInfos ( ),
2093 _writtenFCs ( ),
2094 _nodeCount (0 ),
2095 _currentNodeCount(0 )
2097 if(_defaultEnterFunctors)
2098 _enterFunctors = *_defaultEnterFunctors;
2100 if(_defaultLeaveFunctors)
2101 _leaveFunctors = *_defaultLeaveFunctors;
2105 /** \brief Copy-Constructor
2108 VRMLWriteAction::VRMLWriteAction(const VRMLWriteAction &source) :
2109 Inherited (source ),
2110 _material (source._material ),
2111 _uiIndent (source._uiIndent ),
2112 _pFile (NULL ),
2113 _eTraversalMode (source._eTraversalMode ),
2114 _currentUse (source._currentUse ),
2115 _uiOptions (source._uiOptions ),
2116 _vFCInfos (source._vFCInfos ),
2117 _writtenFCs (source._writtenFCs ),
2118 _nodeCount (source._nodeCount ),
2119 _currentNodeCount(source._currentNodeCount)
2121 if(_defaultEnterFunctors)
2122 _enterFunctors = *_defaultEnterFunctors;
2124 if(_defaultLeaveFunctors)
2125 _leaveFunctors = *_defaultLeaveFunctors;
2128 /** \brief create a new action
2131 VRMLWriteAction *VRMLWriteAction::create( void )
2133 VRMLWriteAction * act;
2135 if(_prototype)
2136 act = new VRMLWriteAction(*_prototype);
2137 else
2138 act = new VRMLWriteAction();
2140 return act;
2144 /** \brief Destructor
2147 VRMLWriteAction::~VRMLWriteAction(void)
2151 /*------------------------------ access -----------------------------------*/
2153 /*---------------------------- properties ---------------------------------*/
2155 void VRMLWriteAction::setMaterial(Material *material)
2157 _material = material;
2160 bool VRMLWriteAction::open(const Char8 *szFilename)
2162 if(szFilename != NULL)
2164 _pFile = fopen(szFilename, "w");
2166 if(_pFile != NULL)
2168 fprintf(_pFile, "#VRML V2.0 utf8 \n");
2172 return _pFile != NULL;
2175 void VRMLWriteAction::close(void)
2177 if(_pFile != NULL)
2179 fclose(_pFile);
2183 void VRMLWriteAction::addOptions(UInt32 uiOptions)
2185 _uiOptions |= uiOptions;
2188 void VRMLWriteAction::subOptions(UInt32 uiOptions)
2190 _uiOptions &= ~uiOptions;
2193 UInt32 VRMLWriteAction::getOptions(void)
2195 return _uiOptions;
2198 Action::ResultE VRMLWriteAction::write(Node *node)
2200 Action::ResultE returnValue = Action::Continue;
2202 _eTraversalMode = OSGCollectFC;
2204 clearInfos();
2206 _writtenFCs.clear();
2208 setMaterial(NULL);
2210 SceneFileHandler::the()->updateWriteProgress(0);
2211 _nodeCount = 0;
2212 _currentNodeCount = 0;
2214 returnValue = Inherited::apply(node);
2216 if(returnValue == Action::Continue)
2218 _eTraversalMode = OSGWrite;
2219 returnValue = Inherited::apply(node);
2222 SceneFileHandler::the()->updateReadProgress(100);
2224 clearInfos();
2226 return returnValue;
2229 /*-------------------------- your_category---------------------------------*/
2231 /*-------------------------- assignment -----------------------------------*/
2233 /** \brief assignment
2238 DrawAction& DrawAction::operator = (const DrawAction &source)
2240 if (this == &source)
2241 return *this;
2243 // copy parts inherited from parent
2244 *(static_cast<Inherited *>(this)) = source;
2246 // free mem alloced by members of 'this'
2248 // alloc new mem for members
2250 // copy
2255 /*-------------------------- comparison -----------------------------------*/
2257 /** \brief assignment
2260 bool VRMLWriteAction::operator < (const VRMLWriteAction &other) const
2262 return this < &other;
2265 /** \brief equal
2268 bool VRMLWriteAction::operator == (
2269 const VRMLWriteAction &OSG_CHECK_ARG(other)) const
2271 return false;
2274 /** \brief unequal
2277 bool VRMLWriteAction::operator != (const VRMLWriteAction &other) const
2279 return ! (*this == other);
2283 /*-------------------------------------------------------------------------*\
2284 - protected -
2285 \*-------------------------------------------------------------------------*/
2288 std::vector<VRMLWriteAction::Functor> *
2289 VRMLWriteAction::getDefaultEnterFunctors(void)
2291 return _defaultEnterFunctors;
2294 std::vector<VRMLWriteAction::Functor> *
2295 VRMLWriteAction::getDefaultLeaveFunctors(void)
2297 return _defaultLeaveFunctors;
2300 Action::ResultE VRMLWriteAction::apply(std::vector<Node *>::iterator begin,
2301 std::vector<Node *>::iterator end)
2303 return Inherited::apply(begin, end);
2306 Action::ResultE VRMLWriteAction::apply(Node * const node)
2308 return Inherited::apply(node);
2311 /*-------------------------------------------------------------------------*\
2312 - private -
2313 \*-------------------------------------------------------------------------*/
2317 ///---------------------------------------------------------------------------
2318 /// FUNCTION:
2319 ///---------------------------------------------------------------------------
2320 //: Example for the head comment of a function
2321 ///---------------------------------------------------------------------------
2323 //p: Paramaters:
2324 //p:
2326 //g: GlobalVars:
2327 //g:
2329 //r: Return:
2330 //r:
2332 //c: Caution:
2333 //c:
2335 //a: Assumptions:
2336 //a:
2338 //d: Description:
2339 //d:
2341 //s: SeeAlso:
2342 //s:
2343 ///---------------------------------------------------------------------------