mirror of
https://github.com/IfcOpenShell/IfcOpenShell.git
synced 2026-08-09 09:21:46 +00:00
Profiles UI - add safety check for missing profiles #6284
Example - https://imgur.com/a/bVdV5oB
This commit is contained in:
@@ -21,6 +21,7 @@ import bpy.utils
|
||||
import bpy.utils.previews
|
||||
import ifcopenshell.util.doc
|
||||
import bonsai.tool as tool
|
||||
from typing import Any
|
||||
|
||||
|
||||
def refresh():
|
||||
@@ -28,7 +29,7 @@ def refresh():
|
||||
|
||||
|
||||
class ProfileData:
|
||||
data = {}
|
||||
data: dict[str, Any] = {}
|
||||
failed_previews: set[int] = set()
|
||||
preview_collection = bpy.utils.previews.new()
|
||||
is_loaded = False
|
||||
@@ -37,6 +38,7 @@ class ProfileData:
|
||||
def load(cls):
|
||||
cls.data = {
|
||||
"total_profiles": cls.total_profiles(),
|
||||
"does_active_profile_exist": cls.does_active_profile_exist(),
|
||||
"active_profile_users": cls.active_profile_users(),
|
||||
"profile_classes": cls.profile_classes(),
|
||||
"is_arbitrary_profile": cls.is_arbitrary_profile(),
|
||||
@@ -50,12 +52,30 @@ class ProfileData:
|
||||
return len([p for p in tool.Ifc.get().by_type("IfcProfileDef") if p.ProfileName])
|
||||
|
||||
@classmethod
|
||||
def active_profile_users(cls):
|
||||
profiles_props = tool.Profile.get_profile_props()
|
||||
if profiles_props.active_profile_index >= len(profiles_props.profiles):
|
||||
def update_active_profile_data(cls) -> None:
|
||||
cls.data["does_active_profile_exist"] = cls.does_active_profile_exist()
|
||||
cls.data["active_profile_users"] = cls.active_profile_users()
|
||||
|
||||
@classmethod
|
||||
def does_active_profile_exist(cls) -> bool:
|
||||
"""
|
||||
Currently not sure if our UI is always preserving existing named profiles,
|
||||
so this check is added to avoid breaking UI in case of a missing profile.
|
||||
"""
|
||||
active_profile = tool.Profile.get_active_profile_ui()
|
||||
if active_profile is None:
|
||||
return False
|
||||
profile_ifc = tool.Ifc.get_entity_by_id(active_profile.ifc_definition_id)
|
||||
return profile_ifc is not None
|
||||
|
||||
@classmethod
|
||||
def active_profile_users(cls) -> int:
|
||||
active_profile = tool.Profile.get_active_profile_ui()
|
||||
if active_profile is None:
|
||||
return 0
|
||||
profile_ifc = tool.Ifc.get_entity_by_id(active_profile.ifc_definition_id)
|
||||
if profile_ifc is None:
|
||||
return 0
|
||||
profile_prop = profiles_props.profiles[profiles_props.active_profile_index]
|
||||
profile_ifc = tool.Ifc.get().by_id(profile_prop.ifc_definition_id)
|
||||
return tool.Ifc.get().get_total_inverses(profile_ifc)
|
||||
|
||||
@classmethod
|
||||
|
||||
@@ -46,7 +46,9 @@ def get_profile_classes(self: "BIMProfileProperties", context: bpy.types.Context
|
||||
def update_profile_name(self: "Profile", context: bpy.types.Context) -> None:
|
||||
from bonsai.bim.handler import refresh_ui_data
|
||||
|
||||
profile = tool.Ifc.get().by_id(self.ifc_definition_id)
|
||||
profile = tool.Ifc.get_entity_by_id(self.ifc_definition_id)
|
||||
if not profile:
|
||||
return
|
||||
profile.ProfileName = self.name
|
||||
refresh_ui_data()
|
||||
|
||||
@@ -63,15 +65,17 @@ class Profile(PropertyGroup):
|
||||
|
||||
|
||||
def update_active_profile_index(self: "BIMProfileProperties", context: bpy.types.Context) -> None:
|
||||
ProfileData.data["active_profile_users"] = ProfileData.active_profile_users()
|
||||
ProfileData.update_active_profile_data()
|
||||
|
||||
|
||||
class BIMProfileProperties(PropertyGroup):
|
||||
is_editing: BoolProperty(name="Is Editing")
|
||||
profiles: CollectionProperty(name="Profiles", type=Profile)
|
||||
active_profile_index: IntProperty(name="Active Profile Index", update=update_active_profile_index)
|
||||
active_profile_id: IntProperty(name="Active Profile Id")
|
||||
active_arbitrary_profile_id: IntProperty(name="Active Arbitrary Profile Id")
|
||||
active_profile_id: IntProperty(name="Active Profile Id", description="Currently edited profile ID (attributes).")
|
||||
active_arbitrary_profile_id: IntProperty(
|
||||
name="Active Arbitrary Profile Id", description="Currently edited arbitrary profile ID."
|
||||
)
|
||||
profile_attributes: CollectionProperty(name="Profile Attributes", type=Attribute)
|
||||
profile_classes: EnumProperty(items=get_profile_classes, name="Profile Classes")
|
||||
is_filtering_material_profiles: bpy.props.BoolProperty(
|
||||
|
||||
@@ -75,6 +75,8 @@ class BIM_PT_profiles(Panel):
|
||||
if not self.props.is_editing:
|
||||
return
|
||||
|
||||
does_active_profile_exist: bool = ProfileData.data["does_active_profile_exist"]
|
||||
|
||||
row = self.layout.row(align=True)
|
||||
if self.props.profile_classes == "IfcArbitraryClosedProfileDef":
|
||||
split = row.split(factor=0.5, align=True)
|
||||
@@ -86,7 +88,14 @@ class BIM_PT_profiles(Panel):
|
||||
row.prop(self.props, "profile_classes", text="")
|
||||
row.operator("bim.add_profile_def", text="", icon="ADD")
|
||||
|
||||
if active_profile:
|
||||
if active_profile and not does_active_profile_exist:
|
||||
box = self.layout.box()
|
||||
box.label(icon="ERROR", text=f"Active profile is missing from IFC project.")
|
||||
row = box.row(align=True)
|
||||
row.label(text="Reload Profiles UI.")
|
||||
row.operator("bim.load_profiles", text="", icon="FILE_REFRESH")
|
||||
|
||||
elif active_profile and does_active_profile_exist:
|
||||
row = self.layout.row(align=True)
|
||||
row.alignment = "RIGHT"
|
||||
|
||||
@@ -122,7 +131,7 @@ class BIM_PT_profiles(Panel):
|
||||
row = self.layout.row()
|
||||
row.prop(self.props, "is_filtering_material_profiles", text="Filter Material Profiles")
|
||||
|
||||
if active_profile:
|
||||
if active_profile and does_active_profile_exist:
|
||||
users_of_profile = ProfileData.data["active_profile_users"]
|
||||
self.layout.label(icon="INFO", text=f"Profile has {users_of_profile} inverse relationship(s) in project")
|
||||
|
||||
|
||||
Reference in New Issue
Block a user