More clever object selection for assigning aggregates #5560

Basically those two properties (Relating Whole and Related Part) are now showing only objects that are valid for the assigning an aggregate - https://i.imgur.com/bqQsXhG.png
This commit is contained in:
Andrej730
2024-10-15 12:28:44 +05:00
parent f17c2eb80e
commit 6c573445dd
+43 -19
View File
@@ -17,6 +17,8 @@
# along with Bonsai. If not, see <http://www.gnu.org/licenses/>.
import bpy
import ifcopenshell.util.element
import bonsai.tool as tool
from bonsai.bim.prop import StrProperty, Attribute
from bonsai.bim.module.spatial.data import SpatialData
from bpy.types import PropertyGroup
@@ -32,29 +34,51 @@ from bpy.props import (
)
def update_relating_object(self, context):
def message(self, context):
self.layout.label(text="Please select a valid IFC Element")
if self.relating_object:
self.related_object = None
if not self.relating_object.BIMObjectProperties.ifc_definition_id:
context.window_manager.popup_menu(message, title="Invalid Element Selected", icon="INFO")
self.relating_object = None
def can_aggregate(relating_obj: bpy.types.Object, related_obj: bpy.types.Object) -> bool:
if related_obj == relating_obj:
return False
# Just a quick way to ignore body representations.
if relating_obj.type != "EMPTY":
return False
if not tool.Aggregate.can_aggregate(relating_obj, related_obj):
return False
return True
def update_related_object(self, context):
def message(self, context):
self.layout.label(text="Please select a valid IFC Element")
def poll_relating_object(self: "BIMObjectAggregateProperties", relating_obj: bpy.types.Object) -> bool:
if (tool.Ifc.get_entity(relating_obj)) is None:
return False
if self.related_object:
self.relating_object = None
if not self.related_object.BIMObjectProperties.ifc_definition_id:
context.window_manager.popup_menu(message, title="Invalid Element Selected", icon="INFO")
self.related_object = None
for related_obj_ in tool.Blender.get_selected_objects():
if not can_aggregate(relating_obj, related_obj_):
return False
return True
def poll_related_object(self: "BIMObjectAggregateProperties", related_obj: bpy.types.Object) -> bool:
if (element := tool.Ifc.get_entity(related_obj)) is None:
return False
aggregate = ifcopenshell.util.element.get_aggregate(element)
if not aggregate:
return False
relating_obj = tool.Ifc.get_object(aggregate)
assert isinstance(relating_obj, bpy.types.Object)
for related_obj_ in tool.Blender.get_selected_objects():
if related_obj_ == related_obj:
return False
if not can_aggregate(relating_obj, related_obj_):
return False
return True
class BIMObjectAggregateProperties(PropertyGroup):
is_editing: BoolProperty(name="Is Editing")
relating_object: PointerProperty(name="Relating Whole", type=bpy.types.Object, update=update_relating_object)
related_object: PointerProperty(name="Related Part", type=bpy.types.Object, update=update_related_object)
relating_object: PointerProperty(name="Relating Whole", type=bpy.types.Object, poll=poll_relating_object)
related_object: PointerProperty(
name="Related Part",
description="Related Part, will be used to derive the Relating Object",
type=bpy.types.Object,
poll=poll_related_object,
)