diff --git a/src/Gui/SoFCDB.cpp b/src/Gui/SoFCDB.cpp index c12c3bde4a..2076baeb0c 100644 --- a/src/Gui/SoFCDB.cpp +++ b/src/Gui/SoFCDB.cpp @@ -42,6 +42,7 @@ #include +#include #include #include #include @@ -497,6 +498,7 @@ bool Gui::SoFCDB::writeToX3D(SoNode* node, bool exportViewpoints, std::string& b return true; } + void Gui::SoFCDB::writeX3DFields( SoNode* node, std::map& nodeMap, @@ -522,7 +524,8 @@ void Gui::SoFCDB::writeX3DFields( } nodeMap[node] = str.str(); - out << " DEF=\"" << str.str() << "\""; + std::string escapedName = Base::Persistence::encodeAttribute(str.str()); + out << " DEF=\"" << escapedName << "\""; } const SoFieldData* fielddata = node->getFieldData(); @@ -545,9 +548,14 @@ void Gui::SoFCDB::writeX3DFields( ba = ba.simplified(); } + // escape XML special characters in attribute value + std::string escapedValue = Base::Persistence::encodeAttribute( + std::string(ba.data()) + ); + out << '\n' << Base::blanks(spaces + 2) << fielddata->getFieldName(i).getString() - << "=\"" << ba.data() << "\" "; + << "=\"" << escapedValue << "\" "; } else { numFieldNodes++; @@ -606,19 +614,19 @@ void Gui::SoFCDB::writeX3DChild( // remove the VRML prefix from the type name std::string sftype(node->getTypeId().getName().getString()); sftype = sftype.substr(4); - out << Base::blanks(spaces) << "<" << sftype << " USE=\"" << mapIt->second << "\" />\n"; + std::string escapedRef = Base::Persistence::encodeAttribute(mapIt->second); + out << Base::blanks(spaces) << "<" << sftype << " USE=\"" << escapedRef << "\" />\n"; } } void Gui::SoFCDB::writeX3D(SoVRMLGroup* node, bool exportViewpoints, std::ostream& out) { out << "\n"; - out << "\n"; - out << "\n"; + out << "\n"; + "xsd:noNamespaceSchemaLocation=\"http://www.web3d.org/specifications/x3d-3.3.xsd\">\n"; out << " \n" " \n" " \n" @@ -685,19 +693,22 @@ bool Gui::SoFCDB::writeToX3DOM(SoNode* node, std::string& buffer) x3d = x3d.erase(0, pos + 1); std::stringstream out; - out << "\n" - << "\n"; + out << "\n"; - out << "\n" + out << "\n" << " \n" - << " \n" - << " \n" - << " \n"; + << " \n" + << " FreeCAD X3DOM Export\n" + << " \n" + << " \n" + << " \n" + << " \n" + << "
\n"; auto onclick = [&out](const char* text) { - out << " \n"; }; @@ -709,9 +720,10 @@ bool Gui::SoFCDB::writeToX3DOM(SoNode* node, std::string& buffer) onclick("Top"); onclick("Bottom"); - out << x3d; + out << "
\n" << x3d; - out << "\n"; + out << " \n" + << "\n"; buffer = out.str();