S
by smr02 on 30 Aug 2024, edited 31 Aug 2024
#
I'm trying to get a brep from freecad and add it to a IFC.
It seems to be working, or at least i can create
#116=IFCSHAPEREPRESENTATION($,'Body','Brep',(#115));
#117=IFCPRODUCTDEFINITIONSHAPE($,$,(#116));
However, in BlenderBIM nothing is displayed.
What am I doing wrong? Attached my files
Her's my code:
import ifcopenshell.api.geometry
import ifcopenshell.util.representation
import ifcopenshell
import ifcopenshell.geom
import ifcopenshell.api
import ifcopenshell.api.root
import freecad
import FreeCAD as F
# FreeCAD
doc = F.open("cube.FCStd")
obj = doc.getObjectsByLabel("Body")[0]
obj_string = obj.Shape.exportBrepToString()
# IFC
model = ifcopenshell.open("empty.ifc")
element = ifcopenshell.api.root.create_entity(model, ifc_class="IfcFurniture")
ifcopenshell.api.geometry.edit_object_placement(model, product=element)
product_definition = ifcopenshell.geom.serialise("IFC4", obj_string, False)
product_definition = model.add(product_definition)
print(product_definition)
element.Representation = product_definition
model.write("cube_test.ifc")
P
by paullee on 30 Aug 2024
#
Work if import back to FreeCAD ?
S
by smr02 on 30 Aug 2024
#
@paullee
No, if i import the IFC in FreeCAD, the geometry also doesn't show
P
by paullee on 30 Aug 2024
#
Apparently, you doesn't export correctly somehow. I export in FreeCAD and re-import and it works :)


P
by paullee on 30 Aug 2024
#
Below are codes generated in FreeCAD console, for reference:-
Python 3.11.9 | packaged by conda-forge | (main, Apr 19 2024, 18:53:30) [GCC 12.3.0] on linux
Type 'help', 'copyright', 'credits' or 'license' for more information.
# Gui.Selection.addSelection('cube','Pad')
### Begin command Std_Export
__objs__ = []
__objs__.append(FreeCAD.getDocument("cube").getObject("Pad"))
import importers.exportIFC
if hasattr(importers.exportIFC, "exportOptions"):
options = importers.exportIFC.exportOptions(u"/... /cube_ Arch_body_ DUMMY.ifc")
importers.exportIFC.export(__objs__, u"/... /cube_ Arch_body_ DUMMY.ifc", options)
else:
importers.exportIFC.export(__objs__, u"/... /cube_ Arch_body_ DUMMY.ifc")
S
by smr02 on 30 Aug 2024
#
I know how to export a IFC from within FreeCAD.
However, I'm trying to export it as a Brep instead of a Mesh to avoid a high Polygon count on more complicated parts.
P
by paullee on 31 Aug 2024
#
+1 votes
Oops, missed that point.
From FreeCAD, export it as Brep by checking the option at Edit - Preference - Export IFC dialog box. You may also check 'User IfcOpenShell Serializer if available'. By both setting, it export and re-imported without problem - both *.ifc attached for reference.
You may have a look at the importers.exportIFC to see how it use IfcOpenShell serialiser.
Python 3.11.9 | packaged by conda-forge | (main, Apr 19 2024, 18:53:30) [GCC 12.3.0] on linux
Type 'help', 'copyright', 'credits' or 'license' for more information.
>>> ### Begin command Std_Export
>>> __objs__ = []
>>> __objs__.append(FreeCAD.getDocument("cube").getObject("Body"))
>>> import importers.exportIFC
>>> if hasattr(importers.exportIFC, "exportOptions"):
>>> options = importers.exportIFC.exportOptions(u"/... / cube-Body_as-BREP_IfcOpenShell.ifc")
>>> importers.exportIFC.export(__objs__, u"/... / cube-Body_as-BREP_IfcOpenShell.ifc", options)
>>> else:
>>> importers.exportIFC.export(__objs__, u"/... / cube-Body_as-BREP_IfcOpenShell.ifc")
>>>
>>> del __objs__
>>> ### End command Std_Export


P
by paullee on 31 Aug 2024
#
I have a look at the exportIFC.py, found some lines which seems relevant to you? Seems similar...
brep_data = sh.removeSplitter().exportBrepToString()
try:
p = geom.serialise(brep_data)
except TypeError:
# IfcOpenShell v0.6.0
# Serialization.cpp:IfcUtil::IfcBaseClass* IfcGeom::serialise(const std::string& schema_name, const TopoDS_Shape& shape, bool advanced)
p = geom.serialise(preferences['SCHEMA'], brep_data)
Full paragraph :-
# new ifcopenshell serializer
from ifcopenshell import geom
serialized = False
if hasattr(geom,"serialise") and obj.isDerivedFrom("Part::Feature") and preferences['SERIALIZE']:
if obj.Shape.Faces:
sh = obj.Shape.copy()
sh.Placement = obj.getGlobalPlacement()
sh.scale(preferences['SCALE_FACTOR']) # to meters
# clean shape and moves placement away from the outer element level
# https://forum.freecad.org/viewtopic.php?p=675760#p675760
brep_data = sh.removeSplitter().exportBrepToString()
try:
p = geom.serialise(brep_data)
except TypeError:
# IfcOpenShell v0.6.0
# Serialization.cpp:IfcUtil::IfcBaseClass* IfcGeom::serialise(const std::string& schema_name, const TopoDS_Shape& shape, bool advanced)
p = geom.serialise(preferences['SCHEMA'], brep_data)
if p:
productdef = ifcfile.add(p)
for rep in productdef.Representations:
rep.ContextOfItems = context
placement = ifcbin.createIfcLocalPlacement()
shapetype = "advancedbrep"
shapes = None
serialized = True
else:
if preferences['DEBUG']:
print(
"Warning! IfcOS serializer did not return a ifc-geometry for object {}. "
"The shape will be exported with triangulation."
.format(obj.Label)
)
P
by paullee on 31 Aug 2024
#
Curious why if IfcOpenShell serialiser is used, the *.ifc become 12.3K from the one without the serialiser 3.1K, 4 times as large?
@yorik Have a gap to comment? :)
Y
by yorik on 31 Aug 2024
#
+1 votes
Just open the two files in a text editor and you'll see why.. The serializer is not optimized for compactness, but on the other hand it recreates a very faithful copy of the brep structure: points -> line -> edge -> wire -> face -> body, everything is there.