mirror of
https://github.com/IfcOpenShell/IfcOpenShell.git
synced 2026-08-11 02:02:22 +00:00
See #1227. Merging doubles gives more reliable results in bisection fills.
This commit is contained in:
@@ -1724,16 +1724,14 @@ class CutDecorator:
|
||||
bm_original.from_mesh(mesh)
|
||||
|
||||
if not (material := ifcopenshell.util.element.get_material(element)):
|
||||
geom = bm_original.verts[:] + bm_original.edges[:] + bm_original.faces[:]
|
||||
verts, tris = self.bisect_mesh_tris(obj, bm_original, geom, context.scene.camera)
|
||||
verts, tris = self.bisect_mesh_tris(obj, bm_original, context.scene.camera)
|
||||
DecoratorData.fill_cache[element_id].setdefault(self.fallback_colour, []).append((verts, tris))
|
||||
return
|
||||
|
||||
if material.is_a() not in ("IfcMaterialLayerSet", "IfcMaterialLayerSetUsage"):
|
||||
# Constituents, lists, and item styles not supported yet
|
||||
material = ifcopenshell.util.element.get_materials(element)[0]
|
||||
geom = bm_original.verts[:] + bm_original.edges[:] + bm_original.faces[:]
|
||||
verts, tris = self.bisect_mesh_tris(obj, bm_original, geom, context.scene.camera)
|
||||
verts, tris = self.bisect_mesh_tris(obj, bm_original, context.scene.camera)
|
||||
colour = self.get_material_colour(material)
|
||||
DecoratorData.fill_cache[element_id].setdefault(colour, []).append((verts, tris))
|
||||
return
|
||||
@@ -1753,8 +1751,7 @@ class CutDecorator:
|
||||
|
||||
if len(layer_set.MaterialLayers) == 1:
|
||||
material = layer_set.MaterialLayers[0].Material
|
||||
geom = bm_original.verts[:] + bm_original.edges[:] + bm_original.faces[:]
|
||||
verts, tris = self.bisect_mesh_tris(obj, bm_original, geom, context.scene.camera)
|
||||
verts, tris = self.bisect_mesh_tris(obj, bm_original, context.scene.camera)
|
||||
colour = self.get_material_colour(material)
|
||||
DecoratorData.fill_cache[element_id].setdefault(colour, []).append((verts, tris))
|
||||
return
|
||||
@@ -1809,8 +1806,7 @@ class CutDecorator:
|
||||
edges = [g for g in bisect["geom_cut"] if isinstance(g, bmesh.types.BMEdge)]
|
||||
fill = bmesh.ops.edgenet_fill(bm_fill, edges=edges)
|
||||
|
||||
geom = bm_fill.verts[:] + bm_fill.edges[:] + bm_fill.faces[:]
|
||||
verts, tris = self.bisect_mesh_tris(obj, bm_fill, geom, context.scene.camera)
|
||||
verts, tris = self.bisect_mesh_tris(obj, bm_fill, context.scene.camera)
|
||||
DecoratorData.fill_cache[element_id].setdefault(colour, []).append((verts, tris))
|
||||
|
||||
verts, edges = self.bisect_mesh(obj, bm, slice_plane_geom, context.scene.camera)
|
||||
@@ -1861,18 +1857,19 @@ class CutDecorator:
|
||||
|
||||
return verts, edges
|
||||
|
||||
def bisect_mesh_tris(self, obj, bm, geom, camera):
|
||||
def bisect_mesh_tris(self, obj, bm, camera):
|
||||
camera_matrix = obj.matrix_world.inverted() @ camera.matrix_world
|
||||
plane_co = camera_matrix.translation
|
||||
plane_no = camera_matrix.col[2].xyz
|
||||
|
||||
global_offset = camera.matrix_world.col[2].xyz * -camera.data.clip_start
|
||||
|
||||
geom = bm.verts[:] + bm.edges[:] + bm.faces[:]
|
||||
bmesh.ops.bisect_plane(
|
||||
bm, geom=geom, dist=0.0001, plane_co=plane_co, plane_no=plane_no, clear_inner=True, clear_outer=True
|
||||
)
|
||||
bmesh.ops.remove_doubles(bm, verts=bm.verts[:])
|
||||
fill = bmesh.ops.edgenet_fill(bm, edges=bm.edges[:])
|
||||
bmesh.ops.remove_doubles(bm, verts=bm.verts, dist=1e-6)
|
||||
fill = bmesh.ops.edgenet_fill(bm, edges=bm.edges)
|
||||
triangulate = bmesh.ops.triangulate(bm, faces=fill["faces"])
|
||||
|
||||
vert_map = {}
|
||||
|
||||
@@ -1062,17 +1062,26 @@ class Loader(bonsai.core.tool.Loader):
|
||||
styles[style] = i
|
||||
last_i = len(layer_set.MaterialLayers) - 1
|
||||
for i, layer in enumerate(layer_set.MaterialLayers):
|
||||
prev_co = co.copy()
|
||||
co += no * layer.LayerThickness * cls.unit_scale
|
||||
if i != last_i:
|
||||
prev_co = co.copy()
|
||||
co += no * layer.LayerThickness * cls.unit_scale
|
||||
bisect_geom = bmesh.ops.bisect_plane(
|
||||
bm, geom=bm.verts[:] + bm.edges[:] + bm.faces[:], dist=0.0001, plane_co=co, plane_no=no
|
||||
)
|
||||
bmesh.ops.duplicate(bm, geom=bisect_geom["geom_cut"])
|
||||
if style := ifcopenshell.util.representation.get_material_style(layer.Material, body):
|
||||
if (material_index := styles.get(style, None)) is None:
|
||||
material_index = len(mesh.materials)
|
||||
mesh.materials.append(tool.Ifc.get_object(style))
|
||||
if not (style := ifcopenshell.util.representation.get_material_style(layer.Material, body)):
|
||||
continue
|
||||
if (material_index := styles.get(style, None)) is None:
|
||||
material_index = len(mesh.materials)
|
||||
mesh.materials.append(tool.Ifc.get_object(style))
|
||||
if i == last_i:
|
||||
for face in bisect_geom["geom"]:
|
||||
if isinstance(face, bmesh.types.BMFace):
|
||||
center = face.calc_center_median()
|
||||
if (center - co).dot(no) >= 0:
|
||||
face.material_index = material_index
|
||||
has_layer_styles = True
|
||||
else:
|
||||
for face in bisect_geom["geom"]:
|
||||
if isinstance(face, bmesh.types.BMFace):
|
||||
center = face.calc_center_median()
|
||||
|
||||
Reference in New Issue
Block a user