Allow manually specified qto values to be exported

This commit is contained in:
Dion Moult
2020-03-19 18:16:30 +11:00
parent 7fe067498f
commit 5454c5b1e7
5 changed files with 79 additions and 41 deletions
@@ -66,6 +66,7 @@ if bpy is not None:
operator.RemovePset,
operator.AddOverridePset,
operator.RemoveOverridePset,
operator.AddQto,
operator.RemoveQto,
operator.AddMaterialPset,
operator.RemoveMaterialPset,
+57 -41
View File
@@ -141,7 +141,6 @@ class IfcParser():
self.load_representations()
self.materials = self.get_materials()
self.styled_items = self.get_styled_items()
self.qtos = self.get_qtos()
self.spatial_structure_elements = self.get_spatial_structure_elements()
self.structural_analysis_models = self.get_structural_analysis_models()
@@ -448,17 +447,8 @@ class IfcParser():
self.rel_defines_by_pset.setdefault(
'{}/{}'.format(pset.name, pset.file), []).append(product)
for pset in obj.BIMObjectProperties.override_psets:
pset_key = '{}/{}'.format(pset.name, obj.name)
raw = {p.name: p.string_value for p in pset.properties if p.string_value}
if not raw:
continue
self.psets[pset_key] = {
'ifc': None,
'raw': raw,
'attributes': { 'Name': pset.name }
}
self.rel_defines_by_pset.setdefault(pset_key, []).append(product)
self.get_product_psets_qtos(product, obj, is_pset=True)
self.get_product_psets_qtos(product, obj, is_qto=True)
for document in obj.BIMObjectProperties.documents:
self.rel_associates_document_object.setdefault(
@@ -490,6 +480,27 @@ class IfcParser():
return product
def get_product_psets_qtos(self, product, obj, is_pset=False, is_qto=False):
if is_pset:
psets_qtos = obj.BIMObjectProperties.override_psets
results = self.psets
relationships = self.rel_defines_by_pset
if is_qto:
psets_qtos = obj.BIMObjectProperties.qtos
results = self.qtos
relationships = self.rel_defines_by_qto
for item in psets_qtos:
item_key = '{}/{}'.format(item.name, obj.name)
raw = {p.name: p.string_value for p in item.properties if p.string_value}
if not raw:
continue
results[item_key] = {
'ifc': None,
'raw': raw,
'attributes': { 'Name': item.name }
}
relationships.setdefault(item_key, []).append(product)
def get_product_relating_structure(self, product, obj):
relating_structure = obj.BIMObjectProperties.relating_structure
if relating_structure:
@@ -918,28 +929,6 @@ class IfcParser():
})
return results
def get_qtos(self):
if not self.ifc_export_settings.has_quantities:
return {}
results = {}
for product in self.selected_products + self.type_products:
obj = product['raw']
if not obj.data:
continue
for property in obj.keys():
if property[0:4] != 'Qto_':
continue
results[obj.name] = {
'ifc': None,
'raw': obj,
'class': property,
'attributes': {
'Name': property,
'MethodOfMeasurement': obj[property]
}
}
return results
def get_type_products(self):
results = []
index = 0
@@ -1316,10 +1305,6 @@ class IfcExporter():
for pset in self.ifc_parser.psets.values():
properties = self.create_pset_properties(pset)
if not properties:
self.ifc_export_settings.logger.error(
'No properties could be detected for the pset {}/{}'.format(
pset['attributes']['Name'],
pset['attributes']['Description']))
continue
pset['attributes'].update({
'GlobalId': ifcopenshell.guid.new(),
@@ -1338,6 +1323,10 @@ class IfcExporter():
'Material': material['ifc']
})
def create_qto_properties(self, qto):
if qto['attributes']['Name'] in schema.ifc.qtos:
return self.create_templated_qto_properties(qto)
def create_pset_properties(self, pset):
if pset['attributes']['Name'] in schema.ifc.psets:
return self.create_templated_pset_properties(pset)
@@ -1382,6 +1371,30 @@ class IfcExporter():
invalid_pset_keys))
return properties
def create_templated_qto_properties(self, qto):
properties = []
templates = schema.ifc.qtos[qto['attributes']['Name']]['HasPropertyTemplates']
for name, data in templates.items():
if name not in qto['raw']:
continue
if data.TemplateType[0:2] == 'Q_':
value_basename = data.TemplateType[2:].title()
value_name = f'{value_basename}Value'
class_name = f'IfcQuantity{value_basename}'
properties.append(
self.file.create_entity(class_name, **{
'Name': name,
value_name: float(qto['raw'][name])
}))
invalid_qto_keys = [k for k in qto['raw'].keys() if k not in templates.keys()]
if invalid_qto_keys:
self.ifc_export_settings.logger.error(
'One or more properties were invalid in the qto {}/{}: {}'.format(
qto['attributes']['Name'],
qto['attributes']['Description'],
invalid_qto_keys))
return properties
def cast_to_base_type(self, var_type, value):
if var_type not in schema.ifc.type_map:
return value
@@ -1676,12 +1689,15 @@ class IfcExporter():
self.create_product(product)
def create_qtos(self):
for object_name, qto in self.ifc_parser.qtos.items():
quantities = self.calculate_quantities(qto['class'], qto['raw'])
# TODO: re-introduce calculated quantities
for qto in self.ifc_parser.qtos.values():
properties = self.create_qto_properties(qto)
if not properties:
continue
qto['attributes'].update({
'GlobalId': ifcopenshell.guid.new(),
'OwnerHistory': self.owner_history,
'Quantities': quantities
'Quantities': properties
})
qto['ifc'] = self.file.create_entity('IfcElementQuantity', **qto['attributes'])
@@ -480,6 +480,22 @@ class RemovePset(bpy.types.Operator):
return {'FINISHED'}
class AddQto(bpy.types.Operator):
bl_idname = 'bim.add_qto'
bl_label = 'Add Qto'
def execute(self, context):
name = bpy.context.active_object.BIMObjectProperties.qto_name
if name not in schema.ifc.qtos:
return {'FINISHED'}
qto = bpy.context.active_object.BIMObjectProperties.qtos.add()
qto.name = name
for prop_name in schema.ifc.qtos[name]['HasPropertyTemplates'].keys():
prop = qto.properties.add()
prop.name = prop_name
return {'FINISHED'}
class AddOverridePset(bpy.types.Operator):
bl_idname = 'bim.add_override_pset'
bl_label = 'Add Override Pset'
+1
View File
@@ -490,6 +490,7 @@ class BIMObjectProperties(PropertyGroup):
material_type: EnumProperty(items=getMaterialTypes, name="Material Type")
override_psets: CollectionProperty(name="Override Psets", type=PsetQto)
override_pset_name: StringProperty(name="Override Pset Name")
qto_name: StringProperty(name="Qto Name")
has_boundary_condition: BoolProperty(name='Has Boundary Condition')
boundary_condition: PointerProperty(name='Boundary Condition', type=BoundaryCondition)
structural_member_connection: PointerProperty(name='Structural Member Connection', type=bpy.types.Object)
+4
View File
@@ -74,6 +74,10 @@ class BIM_PT_object(Panel):
layout.label(text="Quantities:")
row = layout.row(align=True)
row.prop(props, 'qto_name', text='')
row.operator('bim.add_qto')
for index, qto in enumerate(props.qtos):
row = layout.row(align=True)
row.prop(qto, 'name', text='')