mirror of
https://github.com/IfcOpenShell/IfcOpenShell.git
synced 2026-10-01 12:40:07 +00:00
Dumb slabs now auto update thickness based on layer thickness and type changes.
This commit is contained in:
@@ -54,6 +54,7 @@ def register():
|
|||||||
def unregister():
|
def unregister():
|
||||||
bpy.utils.unregister_tool(workspace.WallTool)
|
bpy.utils.unregister_tool(workspace.WallTool)
|
||||||
del bpy.types.Scene.BIMModelProperties
|
del bpy.types.Scene.BIMModelProperties
|
||||||
|
bpy.app.handlers.load_post.remove(handler.load_post)
|
||||||
bpy.types.VIEW3D_MT_mesh_add.remove(grid.add_object_button)
|
bpy.types.VIEW3D_MT_mesh_add.remove(grid.add_object_button)
|
||||||
bpy.types.VIEW3D_MT_mesh_add.remove(stair.add_object_button)
|
bpy.types.VIEW3D_MT_mesh_add.remove(stair.add_object_button)
|
||||||
bpy.types.VIEW3D_MT_mesh_add.remove(door.add_object_button)
|
bpy.types.VIEW3D_MT_mesh_add.remove(door.add_object_button)
|
||||||
|
|||||||
@@ -2,21 +2,15 @@ import bpy
|
|||||||
import ifcopenshell
|
import ifcopenshell
|
||||||
import ifcopenshell.api
|
import ifcopenshell.api
|
||||||
from blenderbim.bim.module.model import product, wall, slab
|
from blenderbim.bim.module.model import product, wall, slab
|
||||||
from blenderbim.bim.ifc import IfcStore
|
|
||||||
from bpy.app.handlers import persistent
|
from bpy.app.handlers import persistent
|
||||||
|
|
||||||
|
|
||||||
@persistent
|
@persistent
|
||||||
def load_post(*args):
|
def load_post(*args):
|
||||||
ifcopenshell.api.add_post_listener("geometry.add_representation", IfcStore.get_file(), product.generate_box)
|
ifcopenshell.api.add_post_listener("geometry.add_representation", None, product.generate_box)
|
||||||
ifcopenshell.api.add_post_listener(
|
ifcopenshell.api.add_post_listener("geometry.add_representation", None, wall.generate_axis)
|
||||||
"geometry.add_representation", IfcStore.get_file(), wall.generate_dumb_wall_axis
|
ifcopenshell.api.add_post_listener("geometry.add_representation", None, wall.calculate_quantities)
|
||||||
)
|
ifcopenshell.api.add_pre_listener("material.edit_layer", None, wall.DumbWallPlaner().regenerate_from_layer)
|
||||||
ifcopenshell.api.add_post_listener(
|
ifcopenshell.api.add_pre_listener("type.assign_type", None, wall.DumbWallPlaner().regenerate_from_type)
|
||||||
"geometry.add_representation", IfcStore.get_file(), wall.calculate_dumb_quantities
|
ifcopenshell.api.add_pre_listener("material.edit_layer", None, slab.DumbSlabPlaner().regenerate_from_layer)
|
||||||
)
|
ifcopenshell.api.add_pre_listener("type.assign_type", None, slab.DumbSlabPlaner().regenerate_from_type)
|
||||||
ifcopenshell.api.add_pre_listener(
|
|
||||||
"material.edit_layer", IfcStore.get_file(), wall.DumbWallPlaner().regenerate_wall_thicknesses_from_layer
|
|
||||||
)
|
|
||||||
ifcopenshell.api.add_pre_listener(
|
|
||||||
"type.assign_type", IfcStore.get_file(), wall.DumbWallPlaner().regenerate_wall_thicknesses_from_type
|
|
||||||
)
|
|
||||||
|
|||||||
@@ -59,6 +59,7 @@ class DumbSlabGenerator:
|
|||||||
modifier.offset = 1
|
modifier.offset = 1
|
||||||
modifier.thickness = self.depth
|
modifier.thickness = self.depth
|
||||||
obj.name = "Slab"
|
obj.name = "Slab"
|
||||||
|
obj.location = self.location
|
||||||
if self.collection_obj and self.collection_obj.BIMObjectProperties.ifc_definition_id:
|
if self.collection_obj and self.collection_obj.BIMObjectProperties.ifc_definition_id:
|
||||||
obj.location[2] = self.collection_obj.location[2] - self.depth
|
obj.location[2] = self.collection_obj.location[2] - self.depth
|
||||||
else:
|
else:
|
||||||
@@ -69,7 +70,64 @@ class DumbSlabGenerator:
|
|||||||
element = self.file.by_id(obj.BIMObjectProperties.ifc_definition_id)
|
element = self.file.by_id(obj.BIMObjectProperties.ifc_definition_id)
|
||||||
pset = ifcopenshell.api.run("pset.add_pset", self.file, product=element, name="EPset_Parametric")
|
pset = ifcopenshell.api.run("pset.add_pset", self.file, product=element, name="EPset_Parametric")
|
||||||
ifcopenshell.api.run("pset.edit_pset", self.file, pset=pset, properties={"Engine": "BlenderBIM.DumbSlab"})
|
ifcopenshell.api.run("pset.edit_pset", self.file, pset=pset, properties={"Engine": "BlenderBIM.DumbSlab"})
|
||||||
ifcopenshell.api.run("material.assign_material", self.file, product=element, type="IfcMaterialLayerSetUsage")
|
|
||||||
MaterialData.load(self.file)
|
MaterialData.load(self.file)
|
||||||
obj.select_set(True)
|
obj.select_set(True)
|
||||||
return obj
|
return obj
|
||||||
|
|
||||||
|
|
||||||
|
class DumbSlabPlaner:
|
||||||
|
def regenerate_from_layer(self, usecase_path, ifc_file, **settings):
|
||||||
|
self.unit_scale = ifcopenshell.util.unit.calculate_unit_scale(ifc_file)
|
||||||
|
layer = settings["layer"]
|
||||||
|
thickness = settings["attributes"].get("LayerThickness")
|
||||||
|
if thickness is None or layer.LayerThickness == thickness:
|
||||||
|
return
|
||||||
|
delta_thickness = thickness - layer.LayerThickness
|
||||||
|
for layer_set in layer.ToMaterialLayerSet:
|
||||||
|
total_thickness = sum([l.LayerThickness for l in layer_set.MaterialLayers])
|
||||||
|
if not total_thickness:
|
||||||
|
continue
|
||||||
|
for inverse in ifc_file.get_inverse(layer_set):
|
||||||
|
if not inverse.is_a("IfcMaterialLayerSetUsage"):
|
||||||
|
continue
|
||||||
|
if ifc_file.schema == "IFC2X3":
|
||||||
|
for rel in ifc_file.get_inverse(inverse):
|
||||||
|
if not rel.is_a("IfcRelAssociatesMaterial"):
|
||||||
|
continue
|
||||||
|
for element in rel.RelatedObjects:
|
||||||
|
self.change_thickness(element, delta_thickness)
|
||||||
|
else:
|
||||||
|
for rel in inverse.AssociatedTo:
|
||||||
|
for element in rel.RelatedObjects:
|
||||||
|
self.change_thickness(element, delta_thickness)
|
||||||
|
|
||||||
|
def regenerate_from_type(self, usecase_path, ifc_file, **settings):
|
||||||
|
self.unit_scale = ifcopenshell.util.unit.calculate_unit_scale(ifc_file)
|
||||||
|
new_material = ifcopenshell.util.element.get_material(settings["relating_type"])
|
||||||
|
if not new_material.is_a("IfcMaterialLayerSet"):
|
||||||
|
return
|
||||||
|
obj = IfcStore.get_element(settings["related_object"].id())
|
||||||
|
if not obj:
|
||||||
|
return
|
||||||
|
current_thickness = obj.dimensions.z / self.unit_scale
|
||||||
|
new_thickness = sum([l.LayerThickness for l in new_material.MaterialLayers])
|
||||||
|
if current_thickness == new_thickness:
|
||||||
|
return
|
||||||
|
self.change_thickness(settings["related_object"], new_thickness - current_thickness)
|
||||||
|
|
||||||
|
def change_thickness(self, element, delta_thickness):
|
||||||
|
parametric = ifcopenshell.util.element.get_psets(element).get("EPset_Parametric")
|
||||||
|
if not parametric or parametric["Engine"] != "BlenderBIM.DumbSlab":
|
||||||
|
return
|
||||||
|
|
||||||
|
obj = IfcStore.get_element(element.id())
|
||||||
|
if not obj:
|
||||||
|
return
|
||||||
|
|
||||||
|
modifier = [m for m in obj.modifiers if m.type == "SOLIDIFY"]
|
||||||
|
if modifier:
|
||||||
|
modifier = modifier[0]
|
||||||
|
else:
|
||||||
|
pass
|
||||||
|
modifier.thickness += delta_thickness * self.unit_scale
|
||||||
|
obj.location[2] -= delta_thickness * self.unit_scale
|
||||||
|
|||||||
@@ -687,7 +687,7 @@ class DumbWallGenerator:
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
def generate_dumb_wall_axis(usecase_path, ifc_file, **settings):
|
def generate_axis(usecase_path, ifc_file, **settings):
|
||||||
axis_context = ifcopenshell.util.representation.get_context(ifc_file, "Model", "Axis", "GRAPH_VIEW")
|
axis_context = ifcopenshell.util.representation.get_context(ifc_file, "Model", "Axis", "GRAPH_VIEW")
|
||||||
if not axis_context:
|
if not axis_context:
|
||||||
return
|
return
|
||||||
@@ -722,7 +722,7 @@ def generate_dumb_wall_axis(usecase_path, ifc_file, **settings):
|
|||||||
bpy.data.meshes.remove(mesh)
|
bpy.data.meshes.remove(mesh)
|
||||||
|
|
||||||
|
|
||||||
def calculate_dumb_quantities(usecase_path, ifc_file, **settings):
|
def calculate_quantities(usecase_path, ifc_file, **settings):
|
||||||
unit_scale = ifcopenshell.util.unit.calculate_unit_scale(ifc_file)
|
unit_scale = ifcopenshell.util.unit.calculate_unit_scale(ifc_file)
|
||||||
obj = settings["blender_object"]
|
obj = settings["blender_object"]
|
||||||
product = ifc_file.by_id(obj.BIMObjectProperties.ifc_definition_id)
|
product = ifc_file.by_id(obj.BIMObjectProperties.ifc_definition_id)
|
||||||
@@ -758,7 +758,7 @@ def calculate_dumb_quantities(usecase_path, ifc_file, **settings):
|
|||||||
|
|
||||||
|
|
||||||
class DumbWallPlaner:
|
class DumbWallPlaner:
|
||||||
def regenerate_wall_thicknesses_from_layer(self, usecase_path, ifc_file, **settings):
|
def regenerate_from_layer(self, usecase_path, ifc_file, **settings):
|
||||||
self.unit_scale = ifcopenshell.util.unit.calculate_unit_scale(ifc_file)
|
self.unit_scale = ifcopenshell.util.unit.calculate_unit_scale(ifc_file)
|
||||||
layer = settings["layer"]
|
layer = settings["layer"]
|
||||||
thickness = settings["attributes"].get("LayerThickness")
|
thickness = settings["attributes"].get("LayerThickness")
|
||||||
@@ -777,13 +777,13 @@ class DumbWallPlaner:
|
|||||||
if not rel.is_a("IfcRelAssociatesMaterial"):
|
if not rel.is_a("IfcRelAssociatesMaterial"):
|
||||||
continue
|
continue
|
||||||
for element in rel.RelatedObjects:
|
for element in rel.RelatedObjects:
|
||||||
self.regenerate_wall_thickness(element, delta_thickness)
|
self.change_thickness(element, delta_thickness)
|
||||||
else:
|
else:
|
||||||
for rel in inverse.AssociatedTo:
|
for rel in inverse.AssociatedTo:
|
||||||
for element in rel.RelatedObjects:
|
for element in rel.RelatedObjects:
|
||||||
self.regenerate_wall_thickness(element, delta_thickness)
|
self.change_thickness(element, delta_thickness)
|
||||||
|
|
||||||
def regenerate_wall_thicknesses_from_type(self, usecase_path, ifc_file, **settings):
|
def regenerate_from_type(self, usecase_path, ifc_file, **settings):
|
||||||
self.unit_scale = ifcopenshell.util.unit.calculate_unit_scale(ifc_file)
|
self.unit_scale = ifcopenshell.util.unit.calculate_unit_scale(ifc_file)
|
||||||
new_material = ifcopenshell.util.element.get_material(settings["relating_type"])
|
new_material = ifcopenshell.util.element.get_material(settings["relating_type"])
|
||||||
if not new_material.is_a("IfcMaterialLayerSet"):
|
if not new_material.is_a("IfcMaterialLayerSet"):
|
||||||
@@ -795,9 +795,9 @@ class DumbWallPlaner:
|
|||||||
new_thickness = sum([l.LayerThickness for l in new_material.MaterialLayers])
|
new_thickness = sum([l.LayerThickness for l in new_material.MaterialLayers])
|
||||||
if current_thickness == new_thickness:
|
if current_thickness == new_thickness:
|
||||||
return
|
return
|
||||||
self.regenerate_wall_thickness(settings["related_object"], new_thickness - current_thickness)
|
self.change_thickness(settings["related_object"], new_thickness - current_thickness)
|
||||||
|
|
||||||
def regenerate_wall_thickness(self, element, delta_thickness):
|
def change_thickness(self, element, delta_thickness):
|
||||||
parametric = ifcopenshell.util.element.get_psets(element).get("EPset_Parametric")
|
parametric = ifcopenshell.util.element.get_psets(element).get("EPset_Parametric")
|
||||||
if not parametric or parametric["Engine"] != "BlenderBIM.DumbWall":
|
if not parametric or parametric["Engine"] != "BlenderBIM.DumbWall":
|
||||||
return
|
return
|
||||||
|
|||||||
@@ -20,4 +20,4 @@ class Usecase:
|
|||||||
continue
|
continue
|
||||||
related_objects = set(rel.RelatedObjects)
|
related_objects = set(rel.RelatedObjects)
|
||||||
related_objects.remove(self.settings["product"])
|
related_objects.remove(self.settings["product"])
|
||||||
rel.RelatedObjects = list(related_object)
|
rel.RelatedObjects = list(related_objects)
|
||||||
|
|||||||
Reference in New Issue
Block a user