Begin drafting out a new representation items panel for managing styles and layers properly

This commit is contained in:
Dion Moult
2023-10-11 23:26:05 +11:00
parent da7f5b015b
commit bf43efe509
5 changed files with 142 additions and 3 deletions
@@ -22,7 +22,9 @@ from . import ui, prop, operator
classes = (
operator.AddRepresentation,
operator.CopyRepresentation,
operator.DisableEditingRepresentationItems,
operator.EditObjectPlacement,
operator.EnableEditingRepresentationItems,
operator.FlipObject,
operator.GetRepresentationIfcParameters,
operator.OverrideDelete,
@@ -47,16 +49,19 @@ classes = (
operator.SwitchRepresentation,
operator.UpdateParametricRepresentation,
operator.UpdateRepresentation,
prop.RepresentationItem,
prop.BIMObjectGeometryProperties,
prop.BIMGeometryProperties,
ui.BIM_PT_placement,
ui.BIM_PT_representations,
ui.BIM_PT_representation_items,
ui.BIM_PT_connections,
ui.BIM_PT_mesh,
ui.BIM_PT_derived_coordinates,
ui.BIM_PT_workarounds,
ui.BIM_MT_object_set_origin,
ui.BIM_MT_separate,
ui.BIM_UL_representation_items,
)
@@ -26,6 +26,7 @@ def refresh():
PlacementData.is_loaded = False
DerivedCoordinatesData.is_loaded = False
RepresentationsData.is_loaded = False
RepresentationItemsData.is_loaded = False
ConnectionsData.is_loaded = False
@@ -92,6 +93,34 @@ class RepresentationsData:
return results
class RepresentationItemsData:
data = {}
is_loaded = False
@classmethod
def load(cls):
cls.data = {"total_items": cls.total_items()}
cls.is_loaded = True
@classmethod
def total_items(cls):
active_representation_id = None
result = 0
if bpy.context.active_object.data and hasattr(bpy.context.active_object.data, "BIMMeshProperties"):
active_representation_id = bpy.context.active_object.data.BIMMeshProperties.ifc_definition_id
element = tool.Ifc.get().by_id(active_representation_id)
if not element.is_a("IfcShapeRepresentation"):
return 0
queue = list(element.Items)
while queue:
item = queue.pop()
if item.is_a("IfcMappedItem"):
queue.extend(item.MappingSource.MappedRepresentation.Items)
else:
result += 1
return result
class ConnectionsData:
data = {}
is_loaded = False
@@ -1727,3 +1727,53 @@ class FlipObject(bpy.types.Operator):
for obj in context.selected_objects:
tool.Geometry.flip_object(obj, self.flip_local_axes)
return {"FINISHED"}
class EnableEditingRepresentationItems(bpy.types.Operator, Operator):
bl_idname = "bim.enable_editing_representation_items"
bl_label = "Enable Editing Representation Items"
bl_options = {"REGISTER", "UNDO"}
def _execute(self, context):
obj = context.active_object
props = obj.BIMGeometryProperties
props.is_editing = True
props.items.clear()
if bpy.context.active_object.data and hasattr(bpy.context.active_object.data, "BIMMeshProperties"):
active_representation_id = bpy.context.active_object.data.BIMMeshProperties.ifc_definition_id
element = tool.Ifc.get().by_id(active_representation_id)
if not element.is_a("IfcShapeRepresentation"):
return
queue = list(element.Items)
while queue:
item = queue.pop()
if item.is_a("IfcMappedItem"):
queue.extend(item.MappingSource.MappedRepresentation.Items)
else:
new = props.items.add()
new.name = item.is_a()
new.ifc_definition_id = item.id()
styles = []
for inverse in tool.Ifc.get().get_inverse(item):
if inverse.is_a("IfcStyledItem"):
styles = inverse.Styles
if styles and styles[0].is_a("IfcPresentationStyleAssignment"):
styles = styles[0].Styles
for style in styles:
if style.is_a("IfcSurfaceStyle"):
new.surface_style = style.Name or "Unnamed"
break
class DisableEditingRepresentationItems(bpy.types.Operator, Operator):
bl_idname = "bim.disable_editing_representation_items"
bl_label = "Disable Editing Representation Items"
bl_options = {"REGISTER", "UNDO"}
def _execute(self, context):
obj = context.active_object
obj.BIMGeometryProperties.is_editing = False
@@ -38,8 +38,17 @@ def get_contexts(self, context):
return RepresentationsData.data["contexts"]
class RepresentationItem(PropertyGroup):
name: StringProperty(name="Name")
surface_style: StringProperty(name="Surface Style")
ifc_definition_id: IntProperty(name="IFC Definition ID")
class BIMObjectGeometryProperties(PropertyGroup):
contexts: EnumProperty(items=get_contexts, name="Contexts")
is_editing: BoolProperty(name="Is Editing", default=False)
items: CollectionProperty(name="Representation Items", type=RepresentationItem)
active_item_index: IntProperty(name="Active Representation Item Index")
class BIMGeometryProperties(PropertyGroup):
@@ -18,11 +18,12 @@
import bpy
import blenderbim.tool as tool
from bpy.types import Panel, Menu
from bpy.types import Panel, Menu, UIList
from blenderbim.bim.ifc import IfcStore
from blenderbim.bim.helper import prop_with_search
from blenderbim.bim.module.geometry.data import (
RepresentationsData,
RepresentationItemsData,
ConnectionsData,
PlacementData,
DerivedCoordinatesData,
@@ -129,6 +130,41 @@ class BIM_PT_representations(Panel):
row.operator("bim.remove_representation", icon="X", text="").representation_id = representation["id"]
class BIM_PT_representation_items(Panel):
bl_label = "Representation Items"
bl_idname = "BIM_PT_representation_items"
bl_space_type = "PROPERTIES"
bl_region_type = "WINDOW"
bl_context = "scene"
bl_order = 1
bl_parent_id = "BIM_PT_tab_representations"
@classmethod
def poll(cls, context):
if not context.active_object:
return False
if not IfcStore.get_element(context.active_object.BIMObjectProperties.ifc_definition_id):
return False
return IfcStore.get_file()
def draw(self, context):
if not RepresentationItemsData.is_loaded:
RepresentationItemsData.load()
props = context.active_object.BIMGeometryProperties
row = self.layout.row(align=True)
row.label(text=f"{RepresentationItemsData.data['total_items']} Items Found")
if props.is_editing:
row.operator("bim.disable_editing_representation_items", icon="CANCEL", text="")
else:
row.operator("bim.enable_editing_representation_items", icon="IMPORT", text="")
return
self.layout.template_list("BIM_UL_representation_items", "", props, "items", props, "active_item_index")
class BIM_PT_connections(Panel):
bl_label = "Connections"
bl_idname = "BIM_PT_connections"
@@ -267,7 +303,7 @@ class BIM_PT_mesh(Panel):
row.prop(ifc_parameter, "name", text="")
row.prop(ifc_parameter, "value", text="")
row.operator("bim.update_parametric_representation", icon="FILE_REFRESH", text="").index = index
class BIM_PT_placement(Panel):
bl_label = "Placement"
@@ -327,7 +363,7 @@ class BIM_PT_derived_coordinates(Panel):
row.label(text="XYZ Dimensions")
row = self.layout.row(align=True)
row.enabled=False
row.enabled = False
row.prop(context.active_object, "dimensions", text="X", index=0, slider=True)
row.prop(context.active_object, "dimensions", text="Y", index=1, slider=True)
row.prop(context.active_object, "dimensions", text="Z", index=2, slider=True)
@@ -379,3 +415,13 @@ class BIM_PT_workarounds(Panel):
row.prop(props, "should_force_triangulation")
row = self.layout.row()
row.prop(props, "should_use_presentation_style_assignment")
class BIM_UL_representation_items(UIList):
def draw_item(self, context, layout, data, item, icon, active_data, active_propname):
if item:
icon = "MATERIAL" if item.surface_style else "MESH_UVSPHERE"
row = layout.row(align=True)
row.label(text=item.name, icon=icon)
if item.surface_style:
row.label(text=item.surface_style)