mirror of
https://github.com/IfcOpenShell/IfcOpenShell.git
synced 2026-09-24 12:36:55 +00:00
Corrects nesting of referents
This commit is contained in:
@@ -62,7 +62,7 @@ from .distance_along_from_station import distance_along_from_station
|
|||||||
from .get_alignment import get_alignment
|
from .get_alignment import get_alignment
|
||||||
from .get_alignment_layout_nest import get_alignment_layout_nest
|
from .get_alignment_layout_nest import get_alignment_layout_nest
|
||||||
from .get_alignment_segment_nest import get_alignment_segment_nest
|
from .get_alignment_segment_nest import get_alignment_segment_nest
|
||||||
from .get_alignment_station import get_alignment_station
|
from .get_alignment_start_station import get_alignment_start_station
|
||||||
from .get_curve_segment_transition_code import get_curve_segment_transition_code
|
from .get_curve_segment_transition_code import get_curve_segment_transition_code
|
||||||
from .get_layout_segments import get_layout_segments
|
from .get_layout_segments import get_layout_segments
|
||||||
from .get_horizontal_layout import get_horizontal_layout
|
from .get_horizontal_layout import get_horizontal_layout
|
||||||
@@ -103,7 +103,7 @@ __all__ = [
|
|||||||
"get_alignment_layout_nest",
|
"get_alignment_layout_nest",
|
||||||
"get_alignment_layouts",
|
"get_alignment_layouts",
|
||||||
"get_alignment_segment_nest",
|
"get_alignment_segment_nest",
|
||||||
"get_alignment_station",
|
"get_alignment_start_station",
|
||||||
"get_axis_subcontext",
|
"get_axis_subcontext",
|
||||||
"get_basis_curve",
|
"get_basis_curve",
|
||||||
"get_cant_layout",
|
"get_cant_layout",
|
||||||
|
|||||||
@@ -83,7 +83,7 @@ def _add_segment_to_layout(file: ifcopenshell.file, layout: entity_instance, seg
|
|||||||
|
|
||||||
# get the station of the start of the segment
|
# get the station of the start of the segment
|
||||||
alignment = ifcopenshell.api.alignment.get_alignment(layout)
|
alignment = ifcopenshell.api.alignment.get_alignment(layout)
|
||||||
start_station = ifcopenshell.api.alignment.get_alignment_station(file, alignment)
|
start_station = ifcopenshell.api.alignment.get_alignment_start_station(file, alignment)
|
||||||
station = start_station + dist_along
|
station = start_station + dist_along
|
||||||
|
|
||||||
# update the zero length layout segment
|
# update the zero length layout segment
|
||||||
@@ -137,8 +137,7 @@ def _add_segment_to_layout(file: ifcopenshell.file, layout: entity_instance, seg
|
|||||||
start_dist_along = segment.DesignParameters.StartDistAlong + segment.DesignParameters.HorizontalLength
|
start_dist_along = segment.DesignParameters.StartDistAlong + segment.DesignParameters.HorizontalLength
|
||||||
zero_length_segment.DesignParameters.StartDistAlong = start_dist_along
|
zero_length_segment.DesignParameters.StartDistAlong = start_dist_along
|
||||||
|
|
||||||
referent_nest = ifcopenshell.api.alignment.get_referent_nest(file, layout)
|
end_referent = zero_length_segment.PositionedRelativeTo[0].RelatingPositioningElement
|
||||||
end_referent = referent_nest.RelatedObjects[-1]
|
|
||||||
end_referent.Name = f"{_get_segment_start_point_label(zero_length_segment,None)} ({ifcopenshell.util.alignment.station_as_string(file,start_station+start_dist_along)})"
|
end_referent.Name = f"{_get_segment_start_point_label(zero_length_segment,None)} ({ifcopenshell.util.alignment.station_as_string(file,start_station+start_dist_along)})"
|
||||||
|
|
||||||
# update the referent's geometric representation's location
|
# update the referent's geometric representation's location
|
||||||
@@ -166,7 +165,7 @@ def _add_segment_to_layout(file: ifcopenshell.file, layout: entity_instance, seg
|
|||||||
end_referent.ObjectPlacement.CartesianPosition.Axis.DirectionRatios = (ax, ay, az)
|
end_referent.ObjectPlacement.CartesianPosition.Axis.DirectionRatios = (ax, ay, az)
|
||||||
end_referent.ObjectPlacement.CartesianPosition.RefDirection.DirectionRatios = (rx, ry, rz)
|
end_referent.ObjectPlacement.CartesianPosition.RefDirection.DirectionRatios = (rx, ry, rz)
|
||||||
|
|
||||||
start_station = ifcopenshell.api.alignment.get_alignment_station(file, alignment)
|
start_station = ifcopenshell.api.alignment.get_alignment_start_station(file, alignment)
|
||||||
end_referent_station = start_station + start_dist_along
|
end_referent_station = start_station + start_dist_along
|
||||||
pset_stationing = ifcopenshell.api.pset.add_pset(file, product=end_referent, name="Pset_Stationing")
|
pset_stationing = ifcopenshell.api.pset.add_pset(file, product=end_referent, name="Pset_Stationing")
|
||||||
ifcopenshell.api.pset.edit_pset(file, pset=pset_stationing, properties={"Station": end_referent_station})
|
ifcopenshell.api.pset.edit_pset(file, pset=pset_stationing, properties={"Station": end_referent_station})
|
||||||
@@ -178,7 +177,7 @@ def _add_segment_to_layout(file: ifcopenshell.file, layout: entity_instance, seg
|
|||||||
prev_segment = segment_nest.RelatedObjects[-3] if 2 < len(segment_nest.RelatedObjects) else None
|
prev_segment = segment_nest.RelatedObjects[-3] if 2 < len(segment_nest.RelatedObjects) else None
|
||||||
name = f"{_get_segment_start_point_label(prev_segment,segment)} ({ifcopenshell.util.alignment.station_as_string(file,station)})"
|
name = f"{_get_segment_start_point_label(prev_segment,segment)} ({ifcopenshell.util.alignment.station_as_string(file,station)})"
|
||||||
referent = ifcopenshell.api.alignment.add_stationing_referent(
|
referent = ifcopenshell.api.alignment.add_stationing_referent(
|
||||||
file, layout, distance_along=dist_along, station=station, name=name, positioned_product=segment
|
file, alignment, distance_along=dist_along, station=station, name=name, positioned_product=segment
|
||||||
)
|
)
|
||||||
ifcopenshell.api.nest.reorder_nesting(file, referent, -1, -1)
|
ifcopenshell.api.nest.reorder_nesting(file, referent, -1, -1)
|
||||||
|
|
||||||
|
|||||||
@@ -51,6 +51,6 @@ def _add_zero_length_segment(file: ifcopenshell.file, layout: entity_instance) -
|
|||||||
segment_nest = ifcopenshell.api.alignment.get_alignment_segment_nest(layout)
|
segment_nest = ifcopenshell.api.alignment.get_alignment_segment_nest(layout)
|
||||||
segment = segment_nest.RelatedObjects[-1]
|
segment = segment_nest.RelatedObjects[-1]
|
||||||
alignment = ifcopenshell.api.alignment.get_alignment(layout)
|
alignment = ifcopenshell.api.alignment.get_alignment(layout)
|
||||||
station = ifcopenshell.api.alignment.get_alignment_station(file, alignment)
|
station = ifcopenshell.api.alignment.get_alignment_start_station(file, alignment)
|
||||||
name = f"{_get_segment_start_point_label(segment,None)} ({ifcopenshell.util.alignment.station_as_string(file,station)})"
|
name = f"{_get_segment_start_point_label(segment,None)} ({ifcopenshell.util.alignment.station_as_string(file,station)})"
|
||||||
ifcopenshell.api.alignment.add_stationing_referent(file, layout, 0.0, station, name, segment)
|
referent = ifcopenshell.api.alignment.add_stationing_referent(file, alignment, 0.0, station, name, segment)
|
||||||
|
|||||||
@@ -30,18 +30,17 @@ import numpy as np
|
|||||||
|
|
||||||
def add_stationing_referent(
|
def add_stationing_referent(
|
||||||
file: ifcopenshell.file,
|
file: ifcopenshell.file,
|
||||||
element: entity_instance,
|
alignment: entity_instance,
|
||||||
distance_along: float,
|
distance_along: float,
|
||||||
station: float,
|
station: float,
|
||||||
name: str,
|
name: str,
|
||||||
positioned_product: entity_instance,
|
positioned_product: entity_instance,
|
||||||
) -> entity_instance:
|
) -> entity_instance:
|
||||||
"""
|
"""
|
||||||
Adds an IfcReferent to the element with the Pset_Stationing property set.
|
Adds an IfcReferent to the alignment with the Pset_Stationing property set.
|
||||||
If element is an IfcAlignment, IfcReferent.PredefinedType is set to "STATION", otherwise "POSITION"
|
|
||||||
|
|
||||||
:param element: the element to receive the referent, expected to be an IfcAlignment or IfcAlignmentSegment
|
:param alignment: the alignment to receive the referent
|
||||||
:param distance_along: distance along the alignment curve
|
:param distance_along: distance along the alignment basis curve
|
||||||
:param station: station value
|
:param station: station value
|
||||||
:param name: name to assign to IfcReferent.Name, typically a stringized version of the station value
|
:param name: name to assign to IfcReferent.Name, typically a stringized version of the station value
|
||||||
:param positioned_product: the product whose position is informed by the referent
|
:param positioned_product: the product whose position is informed by the referent
|
||||||
@@ -52,21 +51,8 @@ def add_stationing_referent(
|
|||||||
.. code:: python
|
.. code:: python
|
||||||
|
|
||||||
alignment = model.by_type("IfcAlignment")[0]
|
alignment = model.by_type("IfcAlignment")[0]
|
||||||
ifcopenshell.api.alignment.add_stationing_referent(model,entity=alignment,distance_along=0.0,station=100.0)
|
ifcopenshell.api.alignment.add_stationing_referent(model,alignment=alignment,distance_along=0.0,station=100.0)
|
||||||
"""
|
"""
|
||||||
alignment = element
|
|
||||||
|
|
||||||
layout_types = [
|
|
||||||
"IfcAlignmentHorizontal",
|
|
||||||
"IfcAlignmentVertical",
|
|
||||||
"IfcAlignmentCant",
|
|
||||||
]
|
|
||||||
|
|
||||||
if element.is_a("IfcAlignmentSegment"):
|
|
||||||
layout = element.Nests[0].RelatingObject
|
|
||||||
alignment = ifcopenshell.api.alignment.get_alignment(layout)
|
|
||||||
elif element.is_a() in layout_types:
|
|
||||||
alignment = ifcopenshell.api.alignment.get_alignment(element)
|
|
||||||
|
|
||||||
basis_curve = ifcopenshell.api.alignment.get_basis_curve(alignment)
|
basis_curve = ifcopenshell.api.alignment.get_basis_curve(alignment)
|
||||||
|
|
||||||
@@ -86,6 +72,8 @@ def add_stationing_referent(
|
|||||||
)
|
)
|
||||||
|
|
||||||
is_valid_curve = True
|
is_valid_curve = True
|
||||||
|
if basis_curve.is_a("IfcCompositeCurve") and len(basis_curve.Segments) == 0:
|
||||||
|
is_valid_curve = False
|
||||||
if basis_curve.is_a("IfcPolyline") and len(basis_curve.Points) < 2:
|
if basis_curve.is_a("IfcPolyline") and len(basis_curve.Points) < 2:
|
||||||
is_valid_curve = False
|
is_valid_curve = False
|
||||||
elif basis_curve.is_a("IfcIndexedPolyCurve") and len(basis_curve.Points.CoordList) < 2:
|
elif basis_curve.is_a("IfcIndexedPolyCurve") and len(basis_curve.Points.CoordList) < 2:
|
||||||
@@ -101,6 +89,7 @@ def add_stationing_referent(
|
|||||||
fn = ifcopenshell_wrapper.convert_loop_to_function_item(fn)
|
fn = ifcopenshell_wrapper.convert_loop_to_function_item(fn)
|
||||||
|
|
||||||
evaluator = ifcopenshell_wrapper.function_item_evaluator(settings, fn)
|
evaluator = ifcopenshell_wrapper.function_item_evaluator(settings, fn)
|
||||||
|
|
||||||
p = evaluator.evaluate(distance_along * unit_scale)
|
p = evaluator.evaluate(distance_along * unit_scale)
|
||||||
p = np.array(p)
|
p = np.array(p)
|
||||||
|
|
||||||
@@ -115,12 +104,23 @@ def add_stationing_referent(
|
|||||||
ax = float(p[0, 2])
|
ax = float(p[0, 2])
|
||||||
ay = float(p[1, 2])
|
ay = float(p[1, 2])
|
||||||
az = float(p[2, 2])
|
az = float(p[2, 2])
|
||||||
|
else:
|
||||||
|
x = 0.
|
||||||
|
y = 0.
|
||||||
|
z = 0.
|
||||||
|
rx = 1.
|
||||||
|
ry = 0.
|
||||||
|
rz = 0.
|
||||||
|
ax = 0.
|
||||||
|
ay = 0.
|
||||||
|
az = 1.
|
||||||
|
|
||||||
object_placement.CartesianPosition = file.createIfcAxis2Placement3D(
|
object_placement.CartesianPosition = file.createIfcAxis2Placement3D(
|
||||||
Location=file.createIfcCartesianPoint((x, y, z)),
|
Location=file.createIfcCartesianPoint((x, y, z)),
|
||||||
Axis=file.createIfcDirection((ax, ay, az)),
|
Axis=file.createIfcDirection((ax, ay, az)),
|
||||||
RefDirection=file.createIfcDirection((rx, ry, rz)),
|
RefDirection=file.createIfcDirection((rx, ry, rz)),
|
||||||
)
|
)
|
||||||
|
|
||||||
# this commented out code is what you would do to add a geometric representation of the referent
|
# this commented out code is what you would do to add a geometric representation of the referent
|
||||||
# the example is a circle. a better way would be to pass a representation into the function
|
# the example is a circle. a better way would be to pass a representation into the function
|
||||||
# representation = file.create_entity(
|
# representation = file.create_entity(
|
||||||
@@ -130,7 +130,6 @@ def add_stationing_referent(
|
|||||||
# )
|
# )
|
||||||
|
|
||||||
# create referent for the station
|
# create referent for the station
|
||||||
predefined_type = "STATION" if element.is_a("IfcAlignment") else "POSITION"
|
|
||||||
referent = file.createIfcReferent(
|
referent = file.createIfcReferent(
|
||||||
GlobalId=ifcopenshell.guid.new(),
|
GlobalId=ifcopenshell.guid.new(),
|
||||||
OwnerHistory=None,
|
OwnerHistory=None,
|
||||||
@@ -139,14 +138,16 @@ def add_stationing_referent(
|
|||||||
ObjectType=None,
|
ObjectType=None,
|
||||||
ObjectPlacement=object_placement,
|
ObjectPlacement=object_placement,
|
||||||
Representation=representation,
|
Representation=representation,
|
||||||
PredefinedType=predefined_type,
|
PredefinedType="STATION",
|
||||||
)
|
)
|
||||||
pset_stationing = ifcopenshell.api.pset.add_pset(file, product=referent, name="Pset_Stationing")
|
pset_stationing = ifcopenshell.api.pset.add_pset(file, product=referent, name="Pset_Stationing")
|
||||||
ifcopenshell.api.pset.edit_pset(file, pset=pset_stationing, properties={"Station": station})
|
ifcopenshell.api.pset.edit_pset(file, pset=pset_stationing, properties={"Station": station})
|
||||||
|
|
||||||
nest = ifcopenshell.api.alignment.get_referent_nest(file, element)
|
nest = ifcopenshell.api.alignment.get_referent_nest(file, alignment)
|
||||||
nest.RelatedObjects += (referent,)
|
nest.RelatedObjects += (referent,)
|
||||||
|
|
||||||
|
nest.RelatedObjects = sorted(nest.RelatedObjects,key=lambda x: ifcopenshell.util.element.get_pset(x, name="Pset_Stationing", prop="Station"))
|
||||||
|
|
||||||
if len(referent.Positions) == 0:
|
if len(referent.Positions) == 0:
|
||||||
rel_positions = file.createIfcRelPositions(
|
rel_positions = file.createIfcRelPositions(
|
||||||
GlobalId=ifcopenshell.guid.new(),
|
GlobalId=ifcopenshell.guid.new(),
|
||||||
|
|||||||
@@ -50,9 +50,22 @@ def _move_vertical_layout_to_child_alignment(
|
|||||||
# nest the vertical layout onto the child alignment
|
# nest the vertical layout onto the child alignment
|
||||||
ifcopenshell.api.nest.assign_object(file, related_objects=[vertical_layout], relating_object=child_alignment)
|
ifcopenshell.api.nest.assign_object(file, related_objects=[vertical_layout], relating_object=child_alignment)
|
||||||
|
|
||||||
# aggreage the child alignment to the parent alignment
|
# aggregate the child alignment to the parent alignment
|
||||||
ifcopenshell.api.aggregate.assign_object(file, products=[child_alignment], relating_object=parent_alignment)
|
ifcopenshell.api.aggregate.assign_object(file, products=[child_alignment], relating_object=parent_alignment)
|
||||||
|
|
||||||
|
# move all referents positioning segments of the vertical layout to the referent nest of the child alignment
|
||||||
|
child_referent_nest = ifcopenshell.api.alignment.get_referent_nest(file,child_alignment)
|
||||||
|
parent_referent_nest = ifcopenshell.api.alignment.get_referent_nest(file,parent_alignment)
|
||||||
|
for referent in parent_referent_nest.RelatedObjects:
|
||||||
|
for product in referent.Positions[0].RelatedProducts:
|
||||||
|
if product.is_a("IfcAlignmentSegment") and product.Nests[0].RelatingObject == vertical_layout:
|
||||||
|
#ifcopenshell.api.nest.change_nest(file,referent,child_alignment) - this doesn't work because referent is assigned to child_alignment.IsNestedBy[0].RelatedObjects
|
||||||
|
# and it needs to be assigned to child_alignment.IsNestedBy[1].RelatedObjects
|
||||||
|
# move the referent manually - unassign it and add it to the child alignment's referent nest
|
||||||
|
ifcopenshell.api.nest.unassign_object(file,[referent])
|
||||||
|
child_referent_nest.RelatedObjects += (referent,)
|
||||||
|
|
||||||
|
|
||||||
# if the parent alignment has a representation, move the Axis/Curve3D represention to the child alignment
|
# if the parent alignment has a representation, move the Axis/Curve3D represention to the child alignment
|
||||||
base_curve = ifcopenshell.api.alignment.get_basis_curve(parent_alignment)
|
base_curve = ifcopenshell.api.alignment.get_basis_curve(parent_alignment)
|
||||||
if base_curve:
|
if base_curve:
|
||||||
|
|||||||
@@ -231,8 +231,9 @@ def add_zero_length_segment(file: ifcopenshell.file, layout: entity_instance, in
|
|||||||
|
|
||||||
if include_referent:
|
if include_referent:
|
||||||
alignment = ifcopenshell.api.alignment.get_alignment(layout)
|
alignment = ifcopenshell.api.alignment.get_alignment(layout)
|
||||||
station = ifcopenshell.api.alignment.get_alignment_station(file, alignment)
|
station = ifcopenshell.api.alignment.get_alignment_start_station(file, alignment)
|
||||||
name = f"{_get_segment_start_point_label(zero_length_curve_segment,None)} ({ifcopenshell.util.alignment.station_as_string(file,station)})"
|
name = f"{_get_segment_start_point_label(zero_length_curve_segment,None)} ({ifcopenshell.util.alignment.station_as_string(file,station)})"
|
||||||
ifcopenshell.api.alignment.add_stationing_referent(file, zero_length_curve_segment, 0.0, station, name=name)
|
referent = ifcopenshell.api.alignment.add_stationing_referent(file, alignment, 0.0, station, name, zero_length_curve_segment)
|
||||||
|
referent.Description = f"Positions zero length segment {zero_length_curve_segment.id()}"
|
||||||
|
|
||||||
return True
|
return True
|
||||||
|
|||||||
@@ -79,17 +79,15 @@ def create(
|
|||||||
|
|
||||||
if include_geometry:
|
if include_geometry:
|
||||||
_create_geometric_representation(file, alignment)
|
_create_geometric_representation(file, alignment)
|
||||||
|
|
||||||
for layout in alignment_layouts:
|
|
||||||
_add_zero_length_segment(file, layout)
|
|
||||||
|
|
||||||
if include_geometry:
|
|
||||||
# define stationing
|
|
||||||
name = ifcopenshell.util.alignment.station_as_string(file, start_station)
|
name = ifcopenshell.util.alignment.station_as_string(file, start_station)
|
||||||
referent = ifcopenshell.api.alignment.add_stationing_referent(
|
referent = ifcopenshell.api.alignment.add_stationing_referent(
|
||||||
file, alignment, 0.0, start_station, name, alignment
|
file, alignment, 0.0, start_station, name, alignment
|
||||||
)
|
)
|
||||||
|
|
||||||
|
for layout in alignment_layouts:
|
||||||
|
_add_zero_length_segment(file, layout)
|
||||||
|
|
||||||
# IFC 4.1.4.1.1 Alignment Aggregation To Project
|
# IFC 4.1.4.1.1 Alignment Aggregation To Project
|
||||||
project = file.by_type("IfcProject")[0]
|
project = file.by_type("IfcProject")[0]
|
||||||
if project:
|
if project:
|
||||||
|
|||||||
@@ -53,11 +53,6 @@ def create_as_offset_curve(
|
|||||||
|
|
||||||
_create_offset_curve_representation(file, alignment, offsets)
|
_create_offset_curve_representation(file, alignment, offsets)
|
||||||
|
|
||||||
# define stationing
|
|
||||||
# name = ifcopenshell.util.alignment.station_as_string(file, start_station)
|
|
||||||
# referent = ifcopenshell.api.alignment.add_stationing_referent(file, alignment, 0.0, start_station, name)
|
|
||||||
# ifcopenshell.api.nest.reorder_nesting(file, referent, -1, 0)
|
|
||||||
|
|
||||||
# IFC 4.1.4.1.1 Alignment Aggregation To Project
|
# IFC 4.1.4.1.1 Alignment Aggregation To Project
|
||||||
project = file.by_type("IfcProject")[0]
|
project = file.by_type("IfcProject")[0]
|
||||||
if project:
|
if project:
|
||||||
|
|||||||
@@ -43,6 +43,6 @@ def distance_along_from_station(file: ifcopenshell.file, alignment: entity_insta
|
|||||||
print(dist_along) # 100.00
|
print(dist_along) # 100.00
|
||||||
"""
|
"""
|
||||||
|
|
||||||
start_station = ifcopenshell.api.alignment.get_alignment_station(file, alignment)
|
start_station = ifcopenshell.api.alignment.get_alignment_start_station(file, alignment)
|
||||||
dist_along = station - start_station
|
dist_along = station - start_station
|
||||||
return dist_along
|
return dist_along
|
||||||
|
|||||||
+7
-6
@@ -22,10 +22,10 @@ import ifcopenshell.util.element
|
|||||||
from ifcopenshell import entity_instance
|
from ifcopenshell import entity_instance
|
||||||
|
|
||||||
|
|
||||||
def get_alignment_station(file: ifcopenshell.file, alignment: entity_instance) -> float:
|
def get_alignment_start_station(file: ifcopenshell.file, alignment: entity_instance) -> float:
|
||||||
"""
|
"""
|
||||||
Returns the start station of the alignment. If the alignment is nested by an IfcReferent
|
Returns the start station of the alignment. The starting station is defined by the first nested IfcReferent.
|
||||||
the referent is checked for PredefinedType of STATION and an occurance of Pset_Stationing.Station,
|
This is interpreted to mean the first IfcReferent with an occurance of Pset_Stationing.Station,
|
||||||
otherwise returns 0.0.
|
otherwise returns 0.0.
|
||||||
"""
|
"""
|
||||||
|
|
||||||
@@ -36,12 +36,13 @@ def get_alignment_station(file: ifcopenshell.file, alignment: entity_instance) -
|
|||||||
|
|
||||||
parent_alignment = ifcopenshell.api.alignment.get_parent_alignment(alignment)
|
parent_alignment = ifcopenshell.api.alignment.get_parent_alignment(alignment)
|
||||||
if parent_alignment:
|
if parent_alignment:
|
||||||
start_station = ifcopenshell.api.alignment.get_alignment_station(file, parent_alignment)
|
start_station = ifcopenshell.api.alignment.get_alignment_start_station(file, parent_alignment)
|
||||||
else:
|
else:
|
||||||
components = ifcopenshell.util.element.get_components(alignment)
|
components = ifcopenshell.util.element.get_components(alignment)
|
||||||
for c in components:
|
for c in components:
|
||||||
if c.is_a("IfcReferent") and ifcopenshell.util.element.get_predefined_type(c) == "STATION":
|
if c.is_a("IfcReferent"):
|
||||||
start_station = ifcopenshell.util.element.get_pset(c, name="Pset_Stationing", prop="Station")
|
start_station = ifcopenshell.util.element.get_pset(c, name="Pset_Stationing", prop="Station")
|
||||||
break
|
if not start_station == None:
|
||||||
|
break
|
||||||
|
|
||||||
return start_station
|
return start_station
|
||||||
@@ -20,18 +20,23 @@ import ifcopenshell
|
|||||||
from ifcopenshell import entity_instance
|
from ifcopenshell import entity_instance
|
||||||
|
|
||||||
|
|
||||||
def get_referent_nest(file: ifcopenshell.file, entity: entity_instance) -> entity_instance:
|
def get_referent_nest(file: ifcopenshell.file, alignment: entity_instance) -> entity_instance:
|
||||||
"""
|
"""
|
||||||
Searches for the IfcRelNest that contains IfcReferent. If one is not found, a empty IfcRelNests is created.
|
Searches for the IfcRelNest that contains IfcReferent. If one is not found, a empty IfcRelNests is created.
|
||||||
|
|
||||||
:param file:
|
:param file:
|
||||||
:param entity: any entity that is the parent in a nesting relationship, but intended to be IfcAlignment, IfcAlignmentHorizontal, IfcAlignmentVertical, or IfcAlignmentCant
|
:param alignment: The IfcAlignment which hosts IfcReferent
|
||||||
:return: Returns the IfcRelNests.
|
:return: Returns the IfcRelNests.
|
||||||
"""
|
"""
|
||||||
for nest in entity.IsNestedBy:
|
if not alignment.is_a("IfcAlignment"):
|
||||||
|
raise TypeError(
|
||||||
|
f"Expected IfcAlignment, instead received {alignment.is_a()}"
|
||||||
|
)
|
||||||
|
|
||||||
|
for nest in alignment.IsNestedBy:
|
||||||
for related_object in nest.RelatedObjects:
|
for related_object in nest.RelatedObjects:
|
||||||
if related_object.is_a("IfcReferent"):
|
if related_object.is_a("IfcReferent"):
|
||||||
return nest
|
return nest
|
||||||
|
|
||||||
nest = file.createIfcRelNests(GlobalId=ifcopenshell.guid.new(), RelatingObject=entity, RelatedObjects=[])
|
nest = file.createIfcRelNests(GlobalId=ifcopenshell.guid.new(), RelatingObject=alignment, RelatedObjects=[])
|
||||||
return nest
|
return nest
|
||||||
|
|||||||
@@ -67,11 +67,11 @@ def test_add_segment_to_layout():
|
|||||||
|
|
||||||
_add_segment_to_layout(file, horizontal_alignment, alignment_segment)
|
_add_segment_to_layout(file, horizontal_alignment, alignment_segment)
|
||||||
|
|
||||||
assert len(horizontal_alignment.IsNestedBy) == 2
|
assert len(horizontal_alignment.IsNestedBy) == 1
|
||||||
referent_nest = ifcopenshell.api.alignment.get_referent_nest(file, horizontal_alignment)
|
|
||||||
segment_nest = ifcopenshell.api.alignment.get_alignment_segment_nest(horizontal_alignment)
|
segment_nest = ifcopenshell.api.alignment.get_alignment_segment_nest(horizontal_alignment)
|
||||||
assert len(segment_nest.RelatedObjects) == 2
|
assert len(segment_nest.RelatedObjects) == 2
|
||||||
assert len(referent_nest.RelatedObjects) == 2
|
referent_nest = ifcopenshell.api.alignment.get_referent_nest(file, alignment)
|
||||||
|
assert len(referent_nest.RelatedObjects) == 3
|
||||||
|
|
||||||
|
|
||||||
test_add_segment_to_layout()
|
test_add_segment_to_layout()
|
||||||
|
|||||||
@@ -39,14 +39,17 @@ def test_add_stationing_to_alignment():
|
|||||||
|
|
||||||
alignment = ifcopenshell.api.alignment.create(file, "TestAlignment", start_station=2000.0)
|
alignment = ifcopenshell.api.alignment.create(file, "TestAlignment", start_station=2000.0)
|
||||||
|
|
||||||
for rel in alignment.IsNestedBy:
|
referent_nest = ifcopenshell.api.alignment.get_referent_nest(file,alignment)
|
||||||
for referent in rel.RelatedObjects:
|
referent = referent_nest.RelatedObjects[0]
|
||||||
if referent.is_a("IfcReferent"):
|
|
||||||
assert referent.PredefinedType == "STATION"
|
assert referent.PredefinedType == "STATION"
|
||||||
assert referent.Name == "2+000.000"
|
assert referent.Name == "2+000.000"
|
||||||
assert ifcopenshell.util.element.get_pset(element=referent, name="Pset_Stationing")
|
assert ifcopenshell.util.element.get_pset(element=referent, name="Pset_Stationing")
|
||||||
assert (
|
assert (
|
||||||
ifcopenshell.util.element.get_pset(element=referent, name="Pset_Stationing", prop="Station")
|
ifcopenshell.util.element.get_pset(element=referent, name="Pset_Stationing", prop="Station")
|
||||||
== 2000.0
|
== 2000.0
|
||||||
)
|
)
|
||||||
assert referent.ObjectPlacement != None
|
assert referent.ObjectPlacement != None
|
||||||
|
|
||||||
|
|
||||||
|
test_add_stationing_to_alignment()
|
||||||
@@ -33,9 +33,13 @@ def test_add_vertical_alignment():
|
|||||||
|
|
||||||
assert len(alignment.IsDecomposedBy) == 0 # no child alignments
|
assert len(alignment.IsDecomposedBy) == 0 # no child alignments
|
||||||
assert len(alignment.IsNestedBy) == 2 # nests for layout and referents
|
assert len(alignment.IsNestedBy) == 2 # nests for layout and referents
|
||||||
assert len(alignment.IsNestedBy[0].RelatedObjects) == 1
|
layout_nest = ifcopenshell.api.alignment.get_alignment_layout_nest(alignment)
|
||||||
assert ifcopenshell.api.alignment.get_referent_nest(file, alignment).RelatedObjects[0].is_a("IfcReferent")
|
assert len(layout_nest.RelatedObjects) == 1
|
||||||
assert alignment.IsNestedBy[0].RelatedObjects[0].is_a("IfcAlignmentHorizontal")
|
assert layout_nest.RelatedObjects[0].is_a("IfcAlignmentHorizontal")
|
||||||
|
referent_nest = ifcopenshell.api.alignment.get_referent_nest(file,alignment)
|
||||||
|
assert len(referent_nest.RelatedObjects) == 2
|
||||||
|
assert referent_nest.RelatedObjects[0].is_a("IfcReferent")
|
||||||
|
|
||||||
curve = ifcopenshell.api.alignment.get_curve(alignment)
|
curve = ifcopenshell.api.alignment.get_curve(alignment)
|
||||||
assert curve.is_a("IfcCompositeCurve")
|
assert curve.is_a("IfcCompositeCurve")
|
||||||
|
|
||||||
@@ -43,9 +47,10 @@ def test_add_vertical_alignment():
|
|||||||
|
|
||||||
assert len(alignment.IsDecomposedBy) == 0 # no child alignments
|
assert len(alignment.IsDecomposedBy) == 0 # no child alignments
|
||||||
assert len(alignment.IsNestedBy) == 2
|
assert len(alignment.IsNestedBy) == 2
|
||||||
assert len(alignment.IsNestedBy[0].RelatedObjects) == 2
|
assert len(layout_nest.RelatedObjects) == 2
|
||||||
assert alignment.IsNestedBy[0].RelatedObjects[0].is_a("IfcAlignmentHorizontal")
|
assert layout_nest.RelatedObjects[0].is_a("IfcAlignmentHorizontal")
|
||||||
assert alignment.IsNestedBy[0].RelatedObjects[1].is_a("IfcAlignmentVertical")
|
assert layout_nest.RelatedObjects[1].is_a("IfcAlignmentVertical")
|
||||||
|
|
||||||
curve = ifcopenshell.api.alignment.get_curve(alignment)
|
curve = ifcopenshell.api.alignment.get_curve(alignment)
|
||||||
assert curve.is_a("IfcGradientCurve")
|
assert curve.is_a("IfcGradientCurve")
|
||||||
|
|
||||||
@@ -57,13 +62,14 @@ def test_add_vertical_alignment():
|
|||||||
|
|
||||||
for child_alignment in alignment.IsDecomposedBy[0].RelatedObjects:
|
for child_alignment in alignment.IsDecomposedBy[0].RelatedObjects:
|
||||||
assert child_alignment.is_a("IfcAlignment")
|
assert child_alignment.is_a("IfcAlignment")
|
||||||
assert len(child_alignment.IsNestedBy) == 1 # one nesting relationship for the IfcAlignmentVertical
|
assert len(child_alignment.IsNestedBy) == 2
|
||||||
assert len(child_alignment.IsNestedBy[0].RelatedObjects) == 1 # The IfcAlignmentVertical
|
child_layout_nest = ifcopenshell.api.alignment.get_alignment_layout_nest(child_alignment)
|
||||||
assert child_alignment.IsNestedBy[0].RelatedObjects[0].is_a("IfcAlignmentVertical")
|
assert len(child_layout_nest.RelatedObjects) == 1 # The IfcAlignmentVertical
|
||||||
|
assert child_layout_nest.RelatedObjects[0].is_a("IfcAlignmentVertical")
|
||||||
|
|
||||||
assert len(alignment.IsNestedBy) == 2
|
assert len(alignment.IsNestedBy) == 2
|
||||||
assert len(alignment.IsNestedBy[0].RelatedObjects) == 1
|
assert len(layout_nest.RelatedObjects) == 1
|
||||||
assert alignment.IsNestedBy[0].RelatedObjects[0].is_a("IfcAlignmentHorizontal")
|
assert layout_nest.RelatedObjects[0].is_a("IfcAlignmentHorizontal")
|
||||||
|
|
||||||
|
|
||||||
test_add_vertical_alignment()
|
test_add_vertical_alignment()
|
||||||
|
|||||||
@@ -51,17 +51,16 @@ def test_create_by_pi_method():
|
|||||||
layout_nest = ifcopenshell.api.alignment.get_alignment_layout_nest(alignment)
|
layout_nest = ifcopenshell.api.alignment.get_alignment_layout_nest(alignment)
|
||||||
assert len(layout_nest.RelatedObjects) == 2
|
assert len(layout_nest.RelatedObjects) == 2
|
||||||
|
|
||||||
|
referent_nest = ifcopenshell.api.alignment.get_referent_nest(file,alignment)
|
||||||
|
assert len(referent_nest.RelatedObjects) == 19
|
||||||
|
|
||||||
horizontal_layout = ifcopenshell.api.alignment.get_horizontal_layout(alignment)
|
horizontal_layout = ifcopenshell.api.alignment.get_horizontal_layout(alignment)
|
||||||
horizontal_segment_nest = ifcopenshell.api.alignment.get_alignment_segment_nest(horizontal_layout)
|
horizontal_segment_nest = ifcopenshell.api.alignment.get_alignment_segment_nest(horizontal_layout)
|
||||||
assert len(horizontal_segment_nest.RelatedObjects) == 8
|
assert len(horizontal_segment_nest.RelatedObjects) == 8
|
||||||
horizontal_referent_nest = ifcopenshell.api.alignment.get_referent_nest(file, horizontal_layout)
|
|
||||||
assert len(horizontal_referent_nest.RelatedObjects) == 8
|
|
||||||
|
|
||||||
vertical_layout = ifcopenshell.api.alignment.get_vertical_layout(alignment)
|
vertical_layout = ifcopenshell.api.alignment.get_vertical_layout(alignment)
|
||||||
vertical_segment_nest = ifcopenshell.api.alignment.get_alignment_segment_nest(vertical_layout)
|
vertical_segment_nest = ifcopenshell.api.alignment.get_alignment_segment_nest(vertical_layout)
|
||||||
assert len(vertical_segment_nest.RelatedObjects) == 10
|
assert len(vertical_segment_nest.RelatedObjects) == 10
|
||||||
vertical_referent_nest = ifcopenshell.api.alignment.get_referent_nest(file, vertical_layout)
|
|
||||||
assert len(vertical_referent_nest.RelatedObjects) == 10
|
|
||||||
|
|
||||||
|
|
||||||
test_create_by_pi_method()
|
test_create_by_pi_method()
|
||||||
|
|||||||
@@ -97,36 +97,16 @@ def callback_alignment():
|
|||||||
|
|
||||||
|
|
||||||
def test_with_default_names(default_names_alignment):
|
def test_with_default_names(default_names_alignment):
|
||||||
hlayout = ifcopenshell.api.alignment.get_horizontal_layout(default_names_alignment)
|
referent_nest = ifcopenshell.api.alignment.get_referent_nest(None, default_names_alignment)
|
||||||
referent_nest = ifcopenshell.api.alignment.get_referent_nest(None, hlayout)
|
|
||||||
|
|
||||||
assert "P.O.B." in referent_nest.RelatedObjects[0].Name
|
expected = ["P.O.B", "P.C.", "P.T.", "P.O.E.", "V.P.O.B.", "P.V.C.", "P.V.T.", "V.P.O.E"]
|
||||||
assert "P.C." in referent_nest.RelatedObjects[1].Name
|
for r in referent_nest.RelatedObjects:
|
||||||
assert "P.T." in referent_nest.RelatedObjects[2].Name
|
assert [x in r.Name for x in expected]
|
||||||
assert "P.O.E." in referent_nest.RelatedObjects[-1].Name
|
|
||||||
|
|
||||||
vlayout = ifcopenshell.api.alignment.get_vertical_layout(default_names_alignment)
|
|
||||||
referent_nest = ifcopenshell.api.alignment.get_referent_nest(None, vlayout)
|
|
||||||
|
|
||||||
assert "V.P.O.B." in referent_nest.RelatedObjects[0].Name
|
|
||||||
assert "P.V.C." in referent_nest.RelatedObjects[1].Name
|
|
||||||
assert "P.V.T." in referent_nest.RelatedObjects[2].Name
|
|
||||||
assert "V.P.O.E." in referent_nest.RelatedObjects[-1].Name
|
|
||||||
|
|
||||||
|
|
||||||
def test_with_callbacks(callback_alignment):
|
def test_with_callbacks(callback_alignment):
|
||||||
hlayout = ifcopenshell.api.alignment.get_horizontal_layout(callback_alignment)
|
referent_nest = ifcopenshell.api.alignment.get_referent_nest(None, callback_alignment)
|
||||||
referent_nest = ifcopenshell.api.alignment.get_referent_nest(None, hlayout)
|
|
||||||
|
|
||||||
assert "A" in referent_nest.RelatedObjects[0].Name
|
expected = ["A","Q","Z","a","q","z"]
|
||||||
assert "Q" in referent_nest.RelatedObjects[1].Name
|
for r in referent_nest.RelatedObjects:
|
||||||
assert "Q" in referent_nest.RelatedObjects[2].Name
|
assert [x in r.Name for x in expected]
|
||||||
assert "Z" in referent_nest.RelatedObjects[-1].Name
|
|
||||||
|
|
||||||
vlayout = ifcopenshell.api.alignment.get_vertical_layout(callback_alignment)
|
|
||||||
referent_nest = ifcopenshell.api.alignment.get_referent_nest(None, vlayout)
|
|
||||||
|
|
||||||
assert "a" in referent_nest.RelatedObjects[0].Name
|
|
||||||
assert "q" in referent_nest.RelatedObjects[1].Name
|
|
||||||
assert "q" in referent_nest.RelatedObjects[2].Name
|
|
||||||
assert "z" in referent_nest.RelatedObjects[-1].Name
|
|
||||||
|
|||||||
@@ -58,11 +58,15 @@ def test_vertical_layout_by_pi_method():
|
|||||||
ifcopenshell.api.alignment.layout_vertical_alignment_by_pi_method(file, vlayout, vpoints, lengths)
|
ifcopenshell.api.alignment.layout_vertical_alignment_by_pi_method(file, vlayout, vpoints, lengths)
|
||||||
|
|
||||||
assert len(alignment.IsDecomposedBy) == 0 # no child alignments
|
assert len(alignment.IsDecomposedBy) == 0 # no child alignments
|
||||||
|
|
||||||
assert len(alignment.IsNestedBy) == 2
|
assert len(alignment.IsNestedBy) == 2
|
||||||
referent_nest = ifcopenshell.api.alignment.get_referent_nest(file, alignment)
|
|
||||||
layout_nest = ifcopenshell.api.alignment.get_alignment_layout_nest(alignment)
|
layout_nest = ifcopenshell.api.alignment.get_alignment_layout_nest(alignment)
|
||||||
assert len(referent_nest.RelatedObjects) == 1
|
|
||||||
assert len(layout_nest.RelatedObjects) == 2
|
assert len(layout_nest.RelatedObjects) == 2
|
||||||
|
|
||||||
|
referent_nest = ifcopenshell.api.alignment.get_referent_nest(file, alignment)
|
||||||
|
assert len(referent_nest.RelatedObjects) == 6
|
||||||
|
|
||||||
segment_nest = ifcopenshell.api.alignment.get_alignment_segment_nest(vlayout)
|
segment_nest = ifcopenshell.api.alignment.get_alignment_segment_nest(vlayout)
|
||||||
assert len(segment_nest.RelatedObjects) == 3
|
assert len(segment_nest.RelatedObjects) == 3
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user