mirror of
https://github.com/IfcOpenShell/IfcOpenShell.git
synced 2026-08-10 01:41:57 +00:00
New utility function to get storey elevations with elevation attribute fallback for more compliant sorting of building storey elevations.
This commit is contained in:
@@ -1,26 +1,26 @@
|
||||
import pytest
|
||||
import test.bootstrap
|
||||
import ifcopenshell.api
|
||||
import ifcopenshell.util.element
|
||||
import ifcopenshell.util.element as subject
|
||||
|
||||
|
||||
class TestGetPsetsIFC4(test.bootstrap.IFC4):
|
||||
def test_getting_the_psets_of_a_product_as_a_dictionary(self):
|
||||
element = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWall")
|
||||
assert ifcopenshell.util.element.get_psets(element) == {}
|
||||
assert subject.get_psets(element) == {}
|
||||
pset = ifcopenshell.api.run("pset.add_pset", self.file, product=element, name="name")
|
||||
ifcopenshell.api.run("pset.edit_pset", self.file, pset=pset, properties={"a": "b"})
|
||||
assert ifcopenshell.util.element.get_psets(element) == {"name": {"a": "b"}}
|
||||
assert subject.get_psets(element) == {"name": {"a": "b"}}
|
||||
|
||||
def test_getting_the_psets_of_a_product_type_as_a_dictionary(self):
|
||||
type_element = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWallType")
|
||||
assert ifcopenshell.util.element.get_psets(type_element) == {}
|
||||
assert subject.get_psets(type_element) == {}
|
||||
pset = ifcopenshell.api.run("pset.add_pset", self.file, product=type_element, name="name")
|
||||
ifcopenshell.api.run("pset.edit_pset", self.file, pset=pset, properties={"x": "y"})
|
||||
assert ifcopenshell.util.element.get_psets(type_element) == {"name": {"x": "y"}}
|
||||
assert subject.get_psets(type_element) == {"name": {"x": "y"}}
|
||||
|
||||
def test_getting_psets_from_an_element_which_cannot_have_psets(self):
|
||||
assert ifcopenshell.util.element.get_psets(self.file.create_entity("IfcPerson")) == {}
|
||||
assert subject.get_psets(self.file.create_entity("IfcPerson")) == {}
|
||||
|
||||
|
||||
class TestGetPropertyDefinitionIFC4(test.bootstrap.IFC4):
|
||||
@@ -28,18 +28,18 @@ class TestGetPropertyDefinitionIFC4(test.bootstrap.IFC4):
|
||||
element = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWall")
|
||||
pset = ifcopenshell.api.run("pset.add_pset", self.file, product=element, name="name")
|
||||
ifcopenshell.api.run("pset.edit_pset", self.file, pset=pset, properties={"a": "b"})
|
||||
assert ifcopenshell.util.element.get_property_definition(pset) == {"a": "b"}
|
||||
assert subject.get_property_definition(pset) == {"a": "b"}
|
||||
|
||||
def test_getting_the_properties_of_a_qto(self):
|
||||
element = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWall")
|
||||
qto = ifcopenshell.api.run("pset.add_qto", self.file, product=element, name="name")
|
||||
ifcopenshell.api.run("pset.edit_qto", self.file, qto=qto, properties={"x": 42})
|
||||
assert ifcopenshell.util.element.get_property_definition(qto) == {"x": 42}
|
||||
assert subject.get_property_definition(qto) == {"x": 42}
|
||||
|
||||
def test_getting_the_properties_of_a_predefined_pset(self):
|
||||
pset = self.file.create_entity("IfcDoorLiningProperties", ifcopenshell.guid.new())
|
||||
pset.LiningDepth = 42
|
||||
assert ifcopenshell.util.element.get_property_definition(pset) == {"LiningDepth": 42}
|
||||
assert subject.get_property_definition(pset) == {"LiningDepth": 42}
|
||||
|
||||
|
||||
class TestGetQuantitiesIFC4(test.bootstrap.IFC4):
|
||||
@@ -47,20 +47,20 @@ class TestGetQuantitiesIFC4(test.bootstrap.IFC4):
|
||||
element = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWall")
|
||||
qto = ifcopenshell.api.run("pset.add_qto", self.file, product=element, name="name")
|
||||
ifcopenshell.api.run("pset.edit_qto", self.file, qto=qto, properties={"x": 42})
|
||||
assert ifcopenshell.util.element.get_quantities(qto.Quantities) == {"x": 42}
|
||||
assert subject.get_quantities(qto.Quantities) == {"x": 42}
|
||||
|
||||
|
||||
class TestGetPropertiesIFC4(test.bootstrap.IFC4):
|
||||
def test_getting_no_properties_when_none_are_available(self):
|
||||
element = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWall")
|
||||
pset = ifcopenshell.api.run("pset.add_pset", self.file, product=element, name="name")
|
||||
assert ifcopenshell.util.element.get_properties(pset.HasProperties) == {}
|
||||
assert subject.get_properties(pset.HasProperties) == {}
|
||||
|
||||
def test_getting_single_properties_from_a_list_of_properties(self):
|
||||
element = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWall")
|
||||
pset = ifcopenshell.api.run("pset.add_pset", self.file, product=element, name="name")
|
||||
ifcopenshell.api.run("pset.edit_pset", self.file, pset=pset, properties={"a": "b"})
|
||||
assert ifcopenshell.util.element.get_properties(pset.HasProperties) == {"a": "b"}
|
||||
assert subject.get_properties(pset.HasProperties) == {"a": "b"}
|
||||
|
||||
def test_getting_complex_properties_from_a_list_of_properties(self):
|
||||
element = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWall")
|
||||
@@ -68,7 +68,7 @@ class TestGetPropertiesIFC4(test.bootstrap.IFC4):
|
||||
complex_property = self.file.createIfcComplexProperty(Name="prop", UsageName="usage_name")
|
||||
ifcopenshell.api.run("pset.edit_pset", self.file, pset=complex_property, properties={"a": "b"})
|
||||
pset.HasProperties = [complex_property]
|
||||
assert ifcopenshell.util.element.get_properties(pset.HasProperties) == {
|
||||
assert subject.get_properties(pset.HasProperties) == {
|
||||
"prop": {
|
||||
"UsageName": "usage_name",
|
||||
"id": 4,
|
||||
@@ -83,8 +83,8 @@ class TestGetTypeIFC4(test.bootstrap.IFC4):
|
||||
element = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWall")
|
||||
element_type = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWallType")
|
||||
ifcopenshell.api.run("type.assign_type", self.file, related_object=element, relating_type=element_type)
|
||||
assert ifcopenshell.util.element.get_type(element) == element_type
|
||||
assert ifcopenshell.util.element.get_type(element_type) == element_type
|
||||
assert subject.get_type(element) == element_type
|
||||
assert subject.get_type(element_type) == element_type
|
||||
|
||||
|
||||
class TestGetTypeIFC2X3(test.bootstrap.IFC2X3):
|
||||
@@ -92,8 +92,8 @@ class TestGetTypeIFC2X3(test.bootstrap.IFC2X3):
|
||||
element = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWall")
|
||||
element_type = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWallType")
|
||||
ifcopenshell.api.run("type.assign_type", self.file, related_object=element, relating_type=element_type)
|
||||
assert ifcopenshell.util.element.get_type(element) == element_type
|
||||
assert ifcopenshell.util.element.get_type(element_type) == element_type
|
||||
assert subject.get_type(element) == element_type
|
||||
assert subject.get_type(element_type) == element_type
|
||||
|
||||
|
||||
class TestGetMaterial(test.bootstrap.IFC4):
|
||||
@@ -101,7 +101,7 @@ class TestGetMaterial(test.bootstrap.IFC4):
|
||||
element = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWall")
|
||||
material = ifcopenshell.api.run("material.add_material", self.file)
|
||||
ifcopenshell.api.run("material.assign_material", self.file, product=element, material=material)
|
||||
assert ifcopenshell.util.element.get_material(element) == material
|
||||
assert subject.get_material(element) == material
|
||||
|
||||
def test_getting_a_material_list_of_a_product(self):
|
||||
element = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWall")
|
||||
@@ -109,31 +109,31 @@ class TestGetMaterial(test.bootstrap.IFC4):
|
||||
rel = ifcopenshell.api.run(
|
||||
"material.assign_material", self.file, product=element, type="IfcMaterialList", material=material
|
||||
)
|
||||
assert ifcopenshell.util.element.get_material(element) == rel.RelatingMaterial
|
||||
assert subject.get_material(element) == rel.RelatingMaterial
|
||||
|
||||
def test_getting_a_material_layer_set_of_a_product(self):
|
||||
element = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWall")
|
||||
rel = ifcopenshell.api.run("material.assign_material", self.file, product=element, type="IfcMaterialLayerSet")
|
||||
assert ifcopenshell.util.element.get_material(element) == rel.RelatingMaterial
|
||||
assert subject.get_material(element) == rel.RelatingMaterial
|
||||
|
||||
def test_getting_a_material_profile_set_of_a_product(self):
|
||||
element = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWall")
|
||||
rel = ifcopenshell.api.run("material.assign_material", self.file, product=element, type="IfcMaterialProfileSet")
|
||||
assert ifcopenshell.util.element.get_material(element) == rel.RelatingMaterial
|
||||
assert subject.get_material(element) == rel.RelatingMaterial
|
||||
|
||||
def test_getting_a_material_layer_set_usage_of_a_product(self):
|
||||
element = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWall")
|
||||
rel = ifcopenshell.api.run(
|
||||
"material.assign_material", self.file, product=element, type="IfcMaterialLayerSetUsage"
|
||||
)
|
||||
assert ifcopenshell.util.element.get_material(element) == rel.RelatingMaterial
|
||||
assert subject.get_material(element) == rel.RelatingMaterial
|
||||
|
||||
def test_getting_a_material_profile_set_usage_of_a_product(self):
|
||||
element = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWall")
|
||||
rel = ifcopenshell.api.run(
|
||||
"material.assign_material", self.file, product=element, type="IfcMaterialProfileSetUsage"
|
||||
)
|
||||
assert ifcopenshell.util.element.get_material(element) == rel.RelatingMaterial
|
||||
assert subject.get_material(element) == rel.RelatingMaterial
|
||||
|
||||
def test_getting_a_material_layer_set_indirectly_from_an_assigned_usage(self):
|
||||
element = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWall")
|
||||
@@ -141,7 +141,7 @@ class TestGetMaterial(test.bootstrap.IFC4):
|
||||
"material.assign_material", self.file, product=element, type="IfcMaterialLayerSetUsage"
|
||||
)
|
||||
assert (
|
||||
ifcopenshell.util.element.get_material(element, should_skip_usage=True) == rel.RelatingMaterial.ForLayerSet
|
||||
subject.get_material(element, should_skip_usage=True) == rel.RelatingMaterial.ForLayerSet
|
||||
)
|
||||
|
||||
def test_getting_a_material_profile_set_indirectly_from_an_assigned_usage(self):
|
||||
@@ -150,7 +150,7 @@ class TestGetMaterial(test.bootstrap.IFC4):
|
||||
"material.assign_material", self.file, product=element, type="IfcMaterialProfileSetUsage"
|
||||
)
|
||||
assert (
|
||||
ifcopenshell.util.element.get_material(element, should_skip_usage=True)
|
||||
subject.get_material(element, should_skip_usage=True)
|
||||
== rel.RelatingMaterial.ForProfileSet
|
||||
)
|
||||
|
||||
@@ -160,7 +160,7 @@ class TestGetMaterial(test.bootstrap.IFC4):
|
||||
ifcopenshell.api.run("type.assign_type", self.file, related_object=element, relating_type=element_type)
|
||||
material = ifcopenshell.api.run("material.add_material", self.file)
|
||||
ifcopenshell.api.run("material.assign_material", self.file, product=element_type, material=material)
|
||||
assert ifcopenshell.util.element.get_material(element) == material
|
||||
assert subject.get_material(element) == material
|
||||
|
||||
|
||||
class TestGetContainerIFC4(test.bootstrap.IFC4):
|
||||
@@ -168,7 +168,7 @@ class TestGetContainerIFC4(test.bootstrap.IFC4):
|
||||
element = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWall")
|
||||
building = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcBuilding")
|
||||
ifcopenshell.api.run("spatial.assign_container", self.file, product=element, relating_structure=building)
|
||||
assert ifcopenshell.util.element.get_container(element) == building
|
||||
assert subject.get_container(element) == building
|
||||
|
||||
def test_getting_an_indirect_spatial_container_of_an_element(self):
|
||||
subelement = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWall")
|
||||
@@ -176,7 +176,7 @@ class TestGetContainerIFC4(test.bootstrap.IFC4):
|
||||
building = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcBuilding")
|
||||
ifcopenshell.api.run("spatial.assign_container", self.file, product=element, relating_structure=building)
|
||||
ifcopenshell.api.run("aggregate.assign_object", self.file, product=subelement, relating_object=element)
|
||||
assert ifcopenshell.util.element.get_container(subelement) == building
|
||||
assert subject.get_container(subelement) == building
|
||||
|
||||
def test_getting_nothing_if_we_enforce_only_getting_direct_spatial_containers(self):
|
||||
subelement = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWall")
|
||||
@@ -184,7 +184,7 @@ class TestGetContainerIFC4(test.bootstrap.IFC4):
|
||||
building = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcBuilding")
|
||||
ifcopenshell.api.run("spatial.assign_container", self.file, product=element, relating_structure=building)
|
||||
ifcopenshell.api.run("aggregate.assign_object", self.file, product=subelement, relating_object=element)
|
||||
assert ifcopenshell.util.element.get_container(subelement, should_get_direct=True) is None
|
||||
assert subject.get_container(subelement, should_get_direct=True) is None
|
||||
|
||||
|
||||
class TestGetDecompositionIFC4(test.bootstrap.IFC4):
|
||||
@@ -194,7 +194,7 @@ class TestGetDecompositionIFC4(test.bootstrap.IFC4):
|
||||
building = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcBuilding")
|
||||
ifcopenshell.api.run("spatial.assign_container", self.file, product=element, relating_structure=building)
|
||||
ifcopenshell.api.run("aggregate.assign_object", self.file, product=subelement, relating_object=element)
|
||||
results = ifcopenshell.util.element.get_decomposition(building)
|
||||
results = subject.get_decomposition(building)
|
||||
assert element in results
|
||||
assert subelement in results
|
||||
|
||||
@@ -204,13 +204,13 @@ class TestGetAggregateIFC4(test.bootstrap.IFC4):
|
||||
element = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcWall")
|
||||
subelement = ifcopenshell.api.run("root.create_entity", self.file, ifc_class="IfcCovering")
|
||||
ifcopenshell.api.run("aggregate.assign_object", self.file, product=subelement, relating_object=element)
|
||||
assert ifcopenshell.util.element.get_aggregate(subelement) == element
|
||||
assert subject.get_aggregate(subelement) == element
|
||||
|
||||
|
||||
class TestReplaceAttributeIFC4(test.bootstrap.IFC4):
|
||||
def test_replacing_an_elements_attribute(self):
|
||||
element = self.file.createIfcWall("foo")
|
||||
ifcopenshell.util.element.replace_attribute(element, "foo", "bar")
|
||||
subject.replace_attribute(element, "foo", "bar")
|
||||
assert element.GlobalId == "bar"
|
||||
|
||||
def test_replacing_a_value_in_a_list(self):
|
||||
@@ -218,7 +218,7 @@ class TestReplaceAttributeIFC4(test.bootstrap.IFC4):
|
||||
new = self.file.createIfcWall()
|
||||
rel = self.file.createIfcRelAggregates()
|
||||
rel.RelatedObjects = [old]
|
||||
ifcopenshell.util.element.replace_attribute(rel, old, new)
|
||||
subject.replace_attribute(rel, old, new)
|
||||
assert rel.RelatedObjects == (new,)
|
||||
|
||||
|
||||
@@ -228,15 +228,15 @@ class TestHasElementReferenceIFC4(test.bootstrap.IFC4):
|
||||
new = self.file.createIfcWall()
|
||||
rel = self.file.createIfcRelAggregates()
|
||||
rel.RelatedObjects = [old]
|
||||
assert ifcopenshell.util.element.has_element_reference(rel.RelatedObjects, old) is True
|
||||
assert ifcopenshell.util.element.has_element_reference(rel.RelatedObjects, new) is False
|
||||
assert subject.has_element_reference(rel.RelatedObjects, old) is True
|
||||
assert subject.has_element_reference(rel.RelatedObjects, new) is False
|
||||
|
||||
|
||||
class TestRemoveDeepIFC4(test.bootstrap.IFC4):
|
||||
def test_removing_an_element_along_with_all_direct_attributes_recursively(self):
|
||||
owner = self.file.createIfcOwnerHistory()
|
||||
element = self.file.createIfcWall(GlobalId="id", OwnerHistory=owner)
|
||||
ifcopenshell.util.element.remove_deep(self.file, element)
|
||||
subject.remove_deep(self.file, element)
|
||||
with pytest.raises(RuntimeError):
|
||||
self.file.by_id(1)
|
||||
self.file.by_id(2)
|
||||
@@ -245,7 +245,7 @@ class TestRemoveDeepIFC4(test.bootstrap.IFC4):
|
||||
owner = self.file.createIfcOwnerHistory()
|
||||
element = self.file.createIfcWall(GlobalId="id1", OwnerHistory=owner)
|
||||
element2 = self.file.createIfcWall(GlobalId="id2", OwnerHistory=owner)
|
||||
ifcopenshell.util.element.remove_deep(self.file, element)
|
||||
subject.remove_deep(self.file, element)
|
||||
with pytest.raises(RuntimeError):
|
||||
self.file.by_guid("id1")
|
||||
assert self.file.by_id(1)
|
||||
@@ -255,7 +255,7 @@ class TestRemoveDeepIFC4(test.bootstrap.IFC4):
|
||||
class TestCopyIFC4(test.bootstrap.IFC4):
|
||||
def test_copying_an_element(self):
|
||||
element = self.file.createIfcWall(GlobalId="id", Name="name")
|
||||
element2 = ifcopenshell.util.element.copy(self.file, element)
|
||||
element2 = subject.copy(self.file, element)
|
||||
assert element.is_a() == element2.is_a()
|
||||
assert element.GlobalId != element2.GlobalId
|
||||
assert element.Name == element2.Name
|
||||
@@ -266,7 +266,7 @@ class TestCopyDeepIFC4(test.bootstrap.IFC4):
|
||||
owner = self.file.createIfcOwnerHistory()
|
||||
owner.State = "READWRITE"
|
||||
element = self.file.createIfcWall(GlobalId="id", Name="name", OwnerHistory=owner)
|
||||
element2 = ifcopenshell.util.element.copy_deep(self.file, element)
|
||||
element2 = subject.copy_deep(self.file, element)
|
||||
assert element.OwnerHistory != element2.OwnerHistory
|
||||
assert element.OwnerHistory.State == element2.OwnerHistory.State
|
||||
|
||||
@@ -274,6 +274,6 @@ class TestCopyDeepIFC4(test.bootstrap.IFC4):
|
||||
element = self.file.createIfcWall(Name="name")
|
||||
rel = self.file.createIfcRelAggregates()
|
||||
rel.RelatedObjects = [element]
|
||||
rel2 = ifcopenshell.util.element.copy_deep(self.file, rel)
|
||||
rel2 = subject.copy_deep(self.file, rel)
|
||||
assert rel.RelatedObjects != rel2.RelatedObjects
|
||||
assert rel.RelatedObjects[0].Name == rel2.RelatedObjects[0].Name
|
||||
|
||||
@@ -0,0 +1,25 @@
|
||||
import ifcopenshell
|
||||
import test.bootstrap
|
||||
import ifcopenshell.util.placement as subject
|
||||
|
||||
|
||||
class TestGetStoreyElevationIFC4(test.bootstrap.IFC4):
|
||||
def test_run(self):
|
||||
storey = self.file.createIfcBuildingStorey()
|
||||
placement = self.file.createIfcLocalPlacement()
|
||||
placement.RelativePlacement = self.file.createIfcAxis2Placement3D(
|
||||
self.file.createIfcCartesianPoint((0.0, 0.0, 3.0))
|
||||
)
|
||||
storey.ObjectPlacement = placement
|
||||
assert subject.get_storey_elevation(storey) == 3.0
|
||||
|
||||
def test_getting_the_elevation_if_no_z_location(self):
|
||||
storey = self.file.createIfcBuildingStorey()
|
||||
storey.Elevation = 3.0
|
||||
assert subject.get_storey_elevation(storey) == 3.0
|
||||
|
||||
def test_returning_0_as_a_fallback(self):
|
||||
storey = self.file.createIfcBuildingStorey()
|
||||
assert subject.get_storey_elevation(storey) == 0.0
|
||||
building = self.file.createIfcBuilding()
|
||||
assert subject.get_storey_elevation(building) == 0.0
|
||||
Reference in New Issue
Block a user