sdf_mesh.cpp
Go to the documentation of this file.
1 
29 #include <stdexcept>
30 
31 #include <boost/algorithm/string/classification.hpp>
32 #include <boost/algorithm/string/split.hpp>
33 #include <Eigen/Geometry>
34 #include <tesseract_common/utils.h>
35 #include <tinyxml2.h>
37 
42 #include <tesseract_urdf/utils.h>
43 
44 namespace tesseract_urdf
45 {
46 std::vector<tesseract_geometry::SDFMesh::Ptr> parseSDFMesh(const tinyxml2::XMLElement* xml_element,
47  const tesseract_common::ResourceLocator& locator,
48  bool visual)
49 {
50  std::vector<tesseract_geometry::SDFMesh::Ptr> meshes;
51 
52  std::string filename;
53  if (tesseract_common::QueryStringAttribute(xml_element, "filename", filename) != tinyxml2::XML_SUCCESS)
54  std::throw_with_nested(std::runtime_error("SDFMesh: Missing or failed parsing attribute 'filename'!"));
55 
56  std::string scale_string;
57  Eigen::Vector3d scale(1, 1, 1);
58  if (tesseract_common::QueryStringAttribute(xml_element, "scale", scale_string) == tinyxml2::XML_SUCCESS)
59  {
60  std::vector<std::string> tokens;
61  boost::split(tokens, scale_string, boost::is_any_of(" "), boost::token_compress_on);
62  if (tokens.size() != 3 || !tesseract_common::isNumeric(tokens))
63  std::throw_with_nested(std::runtime_error("SDFMesh: Failed parsing attribute 'scale'!"));
64 
65  double sx{ 0 }, sy{ 0 }, sz{ 0 };
66  // No need to check return values because the tokens are verified above
70 
71  if (!(sx > 0))
72  std::throw_with_nested(std::runtime_error("SDFMesh: Scale x is not greater than zero!"));
73 
74  if (!(sy > 0))
75  std::throw_with_nested(std::runtime_error("SDFMesh: Scale y is not greater than zero!"));
76 
77  if (!(sz > 0))
78  std::throw_with_nested(std::runtime_error("SDFMesh: Scale z is not greater than zero!"));
79 
80  scale = Eigen::Vector3d(sx, sy, sz);
81  }
82 
83  if (visual)
84  meshes = tesseract_geometry::createMeshFromResource<tesseract_geometry::SDFMesh>(
85  locator.locateResource(filename), scale, true, true, true, true, true);
86  else
87  meshes = tesseract_geometry::createMeshFromResource<tesseract_geometry::SDFMesh>(
88  locator.locateResource(filename), scale, true, false);
89 
90  if (meshes.empty())
91  std::throw_with_nested(std::runtime_error("SDFMesh: Error importing meshes from filename: '" + filename + "'!"));
92 
93  return meshes;
94 }
95 
96 tinyxml2::XMLElement* writeSDFMesh(const std::shared_ptr<const tesseract_geometry::SDFMesh>& sdf_mesh,
97  tinyxml2::XMLDocument& doc,
98  const std::string& package_path,
99  const std::string& filename)
100 {
101  if (sdf_mesh == nullptr)
102  std::throw_with_nested(std::runtime_error("SDF Mesh is nullptr and cannot be converted to XML"));
103  tinyxml2::XMLElement* xml_element = doc.NewElement(SDF_MESH_ELEMENT_NAME.data());
104  Eigen::IOFormat eigen_format(Eigen::StreamPrecision, Eigen::DontAlignCols, " ", " ");
105 
106  try
107  {
108  writeMeshToFile(sdf_mesh, trailingSlash(package_path) + noLeadingSlash(filename));
109  }
110  catch (...)
111  {
112  std::throw_with_nested(std::runtime_error("Failed to write convex mesh to file: " + package_path + filename));
113  }
114  xml_element->SetAttribute("filename", makeURDFFilePath(package_path, filename).c_str());
115 
116  if (!sdf_mesh->getScale().isOnes())
117  {
118  std::stringstream scale_string;
119  scale_string << sdf_mesh->getScale().format(eigen_format);
120  xml_element->SetAttribute("scale", scale_string.str().c_str());
121  }
122  return xml_element;
123 }
124 
125 } // namespace tesseract_urdf
mesh_parser.h
sdf_mesh.h
tesseract_urdf::makeURDFFilePath
std::string makeURDFFilePath(const std::string &package_path, const std::string &filename)
Definition: utils.cpp:55
utils.h
resource_locator.h
tesseract_urdf::trailingSlash
std::string trailingSlash(const std::string &path)
Definition: utils.cpp:20
tesseract_common::ResourceLocator::locateResource
virtual std::shared_ptr< Resource > locateResource(const std::string &url) const=0
TESSERACT_COMMON_IGNORE_WARNINGS_PUSH
#define TESSERACT_COMMON_IGNORE_WARNINGS_PUSH
utils.h
tesseract_urdf::parseSDFMesh
std::vector< std::shared_ptr< tesseract_geometry::SDFMesh > > parseSDFMesh(const tinyxml2::XMLElement *xml_element, const tesseract_common::ResourceLocator &locator, bool visual)
Parse xml element sdf_mesh.
Definition: sdf_mesh.cpp:46
tesseract_common::ResourceLocator
tesseract_common::QueryStringAttribute
int QueryStringAttribute(const tinyxml2::XMLElement *xml_element, const char *name, std::string &value)
TESSERACT_COMMON_IGNORE_WARNINGS_POP
tesseract_urdf::writeMeshToFile
void writeMeshToFile(const std::shared_ptr< const tesseract_geometry::PolygonMesh > &mesh, const std::string &filepath)
Definition: utils.cpp:140
tesseract_common::isNumeric
bool isNumeric(const std::string &s)
tesseract_common::toNumeric< double >
template bool toNumeric< double >(const std::string &, double &)
macros.h
tesseract_urdf
Definition: box.h:43
tesseract_urdf::noLeadingSlash
std::string noLeadingSlash(const std::string &filename)
Definition: utils.cpp:45
sdf_mesh.h
tesseract_urdf::SDF_MESH_ELEMENT_NAME
static constexpr std::string_view SDF_MESH_ELEMENT_NAME
Definition: sdf_mesh.h:46
tesseract_urdf::writeSDFMesh
tinyxml2::XMLElement * writeSDFMesh(const std::shared_ptr< const tesseract_geometry::SDFMesh > &sdf_mesh, tinyxml2::XMLDocument &doc, const std::string &package_path, const std::string &filename)
writeSDFMesh Write SDF Mesh to URDF XML. This is non-standard URDF / tesseract-exclusive
Definition: sdf_mesh.cpp:96


tesseract_urdf
Author(s): Levi Armstrong
autogenerated on Thu Apr 24 2025 03:10:44