Vertex de-duplication
Hi team
I am currently wrestling with a mock up of little tool to write IFC files using IfcTesselatedFaceSet and IfcFacetedBrep.
Specifically, I am trying to implement some sort of vertex de-duplication functionality, as the input meshes I want to convert, may not be completely free of duplicate vertices.
Now when handling a creation of an IfcFacetedBrep, I can get rid of the duplicate vertices relatively easily through a mere comparison of the individual vertex coordinates, and simply only create new IfcCartesianPoint instance for unique vertices, and get reference to an existing IfcCartesianPoint instance for all of the duplicate ones.
However, when handling creation of an IfcTesselatedFaceSet, coordinates are written directly into the IfcCartesianPointList3D, which is a mere list of point coordinates, rather than set of separate IfcCartesianPoint class instances I could reference to instead of creating one anew.
I wonder, whether there is any means I may be overlooking, that would help me reduce the duplicate vertices in the case of IfcTesselatedFaceSet as well, or it is by principle simply not possible?
Many thanks,
M.
This is just down to the way the IFC schema is defined.
IfcTriangulatedFaceSet/IfcPolygonalFaceSet define Coordinates as an IfcCartesianPointList (implemented by 2D/3D sub-classes) which stores vertices in a compact form of numeric XYZ triplets rather than a IFC a collection of IfcCartesianPoint primitives.
But the same approach you use to de-deduplicate the IfcCartesianPoints can be used on these more primitive XYZ triplets.
There are some helpers on IfcCartesianPoints that may be helpful here: https://github.com/xBimTeam/XbimEssentials/blob/master/Xbim.Ifc/Extensions/IIfcCartesianPointExtensions.cs
Thank you for your answer, Andy.
Ultimately, my aim would be to prepare my code for a situation when I feed it a number of finely meshed contacting solids, sharing the same spatial boundary over a larger area (leading to a significant number of shared vertices). For this scenario, I shall aim to de-duplicate vertices globally, and not only within the individual input solids.
IfcFacetedBrep facilitates this easily through comparison of the IfcCartesianPoint instances as I have mentioned earlier. However, storing geometry using IfcFacetedBrep has proven to be overall inefficient for my purposes, especially when I expect the resulting file will be used for viewing only.
On the other hand, the suggested solution, ultimately revolving around having one or more (depending on how I set this up) giant global IfcCartesianPointList3D lists of coords/points, to pick face vertex IDs from, may also have its performance drawbacks. I reckon this will simply require me spending some more time with it and test.
Yes, deduplicating vertices globally would be challenging for a IfcCartesianPointList3D - and I'm not sure how much benefit you'd get? Are you seeing much duplication?
Incidentally if you're looking to reduce the size of meshes for rendering, have you seen the recent work to simplify meshes in the GeometryEngine? E.g. This test demos: https://github.com/xBimTeam/XbimGeometry/blob/feature/netcore/Xbim.Geometry.Engine.Tests/MeshSimplificationTests.cs
This is a 'lossy' approach but I suspect it would pick up any duplicated vertices trivially. Of course this won't reduce the size of the IFC but will produce smaller geometry/wexbim outputs.
Also, it shouldn't be hard to implement a "view" of the IfcCartesianPointList3D, which would allow you to see it as a list of points, if that is what you need. If you intend to use one large IfcCartesianPointList3D, you may need to look at spatial indexing with something like Octree to identify your redundant points efficiently.