mirror of
https://github.com/IfcOpenShell/IfcOpenShell.git
synced 2026-09-25 09:32:37 +00:00
Merge pull request #2258 from vulevukusej/create-pset_templates-in-bbim
support enums in new pset_templates
This commit is contained in:
@@ -40,7 +40,7 @@ def draw_attribute(attribute, layout, copy_operator=None):
|
|||||||
return
|
return
|
||||||
if len(attribute.enumerated_values) != 0:
|
if len(attribute.enumerated_values) != 0:
|
||||||
layout.label(text=attribute.name)
|
layout.label(text=attribute.name)
|
||||||
grid = layout.column_flow(columns=4)
|
grid = layout.column_flow(columns=3)
|
||||||
for e in attribute.enumerated_values:
|
for e in attribute.enumerated_values:
|
||||||
grid.prop(
|
grid.prop(
|
||||||
e,
|
e,
|
||||||
|
|||||||
@@ -412,7 +412,7 @@ class BIM_OT_add_property_to_edit(bpy.types.Operator):
|
|||||||
bl_idname = "bim.add_property_to_edit"
|
bl_idname = "bim.add_property_to_edit"
|
||||||
bl_options = {"REGISTER", "UNDO"}
|
bl_options = {"REGISTER", "UNDO"}
|
||||||
option: bpy.props.StringProperty()
|
option: bpy.props.StringProperty()
|
||||||
index: bpy.props.IntProperty()
|
index: bpy.props.IntProperty(default=-1)
|
||||||
|
|
||||||
def execute(self, context):
|
def execute(self, context):
|
||||||
if self.index == -1:
|
if self.index == -1:
|
||||||
|
|||||||
@@ -20,6 +20,8 @@ import bpy
|
|||||||
from . import ui, prop, operator
|
from . import ui, prop, operator
|
||||||
|
|
||||||
classes = (
|
classes = (
|
||||||
|
operator.RefreshPsetTemplates,
|
||||||
|
operator.AddPsetFile,
|
||||||
operator.SavePsetTemplateFile,
|
operator.SavePsetTemplateFile,
|
||||||
operator.AddPsetTemplate,
|
operator.AddPsetTemplate,
|
||||||
operator.EditPsetTemplate,
|
operator.EditPsetTemplate,
|
||||||
@@ -30,8 +32,11 @@ classes = (
|
|||||||
operator.EnableEditingPsetTemplate,
|
operator.EnableEditingPsetTemplate,
|
||||||
operator.DisableEditingPsetTemplate,
|
operator.DisableEditingPsetTemplate,
|
||||||
operator.EnableEditingPropTemplate,
|
operator.EnableEditingPropTemplate,
|
||||||
|
operator.DeletePropEnum,
|
||||||
|
operator.AddPropEnum,
|
||||||
operator.DisableEditingPropTemplate,
|
operator.DisableEditingPropTemplate,
|
||||||
prop.PsetTemplate,
|
prop.PsetTemplate,
|
||||||
|
prop.EnumerationValues,
|
||||||
prop.PropTemplate,
|
prop.PropTemplate,
|
||||||
prop.BIMPsetTemplateProperties,
|
prop.BIMPsetTemplateProperties,
|
||||||
ui.BIM_PT_pset_template,
|
ui.BIM_PT_pset_template,
|
||||||
|
|||||||
@@ -16,16 +16,66 @@
|
|||||||
# You should have received a copy of the GNU General Public License
|
# You should have received a copy of the GNU General Public License
|
||||||
# along with BlenderBIM Add-on. If not, see <http://www.gnu.org/licenses/>.
|
# along with BlenderBIM Add-on. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
|
||||||
|
import os
|
||||||
import bpy
|
import bpy
|
||||||
import ifcopenshell
|
import ifcopenshell
|
||||||
import ifcopenshell.api
|
import ifcopenshell.api
|
||||||
import blenderbim.bim.schema
|
import blenderbim.bim.schema
|
||||||
import blenderbim.bim.handler
|
import blenderbim.bim.handler
|
||||||
from blenderbim.bim.module.pset_template.prop import updatePsetTemplateFiles, updatePsetTemplates, getPsetTemplates
|
from blenderbim.bim.module.pset_template.prop import purge as purge_templates, updatePsetTemplates, getPsetTemplates
|
||||||
|
from blenderbim.bim.module.pset.prop import purge as purge_psets
|
||||||
from ifcopenshell.api.pset_template.data import Data
|
from ifcopenshell.api.pset_template.data import Data
|
||||||
from blenderbim.bim.ifc import IfcStore
|
from blenderbim.bim.ifc import IfcStore
|
||||||
|
|
||||||
|
|
||||||
|
#This is just a temporary operator until
|
||||||
|
#@Moult performs some of his refactor-magic ;) - vulevukusej
|
||||||
|
class RefreshPsetTemplates(bpy.types.Operator):
|
||||||
|
bl_idname = "bim.refresh_psettemplates"
|
||||||
|
bl_label = "Refresh the data for PsetTemplates"
|
||||||
|
bl_options = {"REGISTER", "UNDO"}
|
||||||
|
|
||||||
|
def execute(self, context):
|
||||||
|
purge_templates()
|
||||||
|
purge_psets()
|
||||||
|
return {"FINISHED"}
|
||||||
|
|
||||||
|
|
||||||
|
class AddPsetFile(bpy.types.Operator):
|
||||||
|
bl_idname = "bim.add_pset_file"
|
||||||
|
bl_label = "Add Pset File"
|
||||||
|
bl_options = {"REGISTER", "UNDO"}
|
||||||
|
|
||||||
|
def invoke(self, context, event):
|
||||||
|
return context.window_manager.invoke_props_dialog(self, width=250)
|
||||||
|
|
||||||
|
def draw(self, context):
|
||||||
|
self.props = context.scene.BIMPsetTemplateProperties
|
||||||
|
self.layout.prop(self.props, "new_template_filename", text="Filename:")
|
||||||
|
|
||||||
|
def execute(self, context):
|
||||||
|
template = ifcopenshell.file()
|
||||||
|
filepath = os.path.join(
|
||||||
|
context.scene.BIMProperties.data_dir,
|
||||||
|
"pset",
|
||||||
|
self.props.new_template_filename + ".ifc",
|
||||||
|
)
|
||||||
|
|
||||||
|
template.create_entity(
|
||||||
|
"IFCPROPERTYSETTEMPLATE",
|
||||||
|
**{
|
||||||
|
"GlobalId": ifcopenshell.guid.new(),
|
||||||
|
"Name": "Name",
|
||||||
|
"Description": "Description",
|
||||||
|
"TemplateType": "PSET_TYPEDRIVENONLY",
|
||||||
|
"ApplicableEntity": "IfcTypeObject"
|
||||||
|
}
|
||||||
|
)
|
||||||
|
template.write(filepath)
|
||||||
|
self.props.new_template_filename = ""
|
||||||
|
return {"FINISHED"}
|
||||||
|
|
||||||
|
|
||||||
class AddPsetTemplate(bpy.types.Operator):
|
class AddPsetTemplate(bpy.types.Operator):
|
||||||
bl_idname = "bim.add_pset_template"
|
bl_idname = "bim.add_pset_template"
|
||||||
bl_label = "Add Pset Template"
|
bl_label = "Add Pset Template"
|
||||||
@@ -41,7 +91,6 @@ class AddPsetTemplate(bpy.types.Operator):
|
|||||||
return result
|
return result
|
||||||
|
|
||||||
def _execute(self, context):
|
def _execute(self, context):
|
||||||
props = context.scene.BIMPsetTemplateProperties
|
|
||||||
ifcopenshell.api.run("pset_template.add_pset_template", IfcStore.pset_template_file)
|
ifcopenshell.api.run("pset_template.add_pset_template", IfcStore.pset_template_file)
|
||||||
Data.load(IfcStore.pset_template_file)
|
Data.load(IfcStore.pset_template_file)
|
||||||
updatePsetTemplates(self, context)
|
updatePsetTemplates(self, context)
|
||||||
@@ -139,6 +188,38 @@ class EnableEditingPropTemplate(bpy.types.Operator):
|
|||||||
props.active_prop_template.name = template["Name"] or ""
|
props.active_prop_template.name = template["Name"] or ""
|
||||||
props.active_prop_template.description = template["Description"] or ""
|
props.active_prop_template.description = template["Description"] or ""
|
||||||
props.active_prop_template.primary_measure_type = template["PrimaryMeasureType"]
|
props.active_prop_template.primary_measure_type = template["PrimaryMeasureType"]
|
||||||
|
props.active_prop_template.template_type = template["TemplateType"]
|
||||||
|
props.active_prop_template.enum_values.clear()
|
||||||
|
|
||||||
|
if template["Enumerators"]:
|
||||||
|
props.active_prop_template.enum_values.clear()
|
||||||
|
data_type = props.active_prop_template.get_value_name()
|
||||||
|
for e in template["Enumerators"].EnumerationValues:
|
||||||
|
new = props.active_prop_template.enum_values.add()
|
||||||
|
setattr(new, data_type, e.wrappedValue)
|
||||||
|
|
||||||
|
return {"FINISHED"}
|
||||||
|
|
||||||
|
class DeletePropEnum(bpy.types.Operator):
|
||||||
|
bl_idname = "bim.delete_prop_enum"
|
||||||
|
bl_label = "delete property enumeration"
|
||||||
|
bl_options = {"REGISTER", "UNDO"}
|
||||||
|
index: bpy.props.IntProperty()
|
||||||
|
|
||||||
|
def execute(self, context):
|
||||||
|
active_prop = context.scene.BIMPsetTemplateProperties.active_prop_template
|
||||||
|
active_prop.enum_values.remove(self.index)
|
||||||
|
return {"FINISHED"}
|
||||||
|
|
||||||
|
class AddPropEnum(bpy.types.Operator):
|
||||||
|
bl_idname = "bim.add_prop_enum"
|
||||||
|
bl_label = "add property enumeration"
|
||||||
|
bl_options = {"REGISTER", "UNDO"}
|
||||||
|
index: bpy.props.IntProperty()
|
||||||
|
|
||||||
|
def execute(self, context):
|
||||||
|
active_prop = context.scene.BIMPsetTemplateProperties.active_prop_template
|
||||||
|
active_prop.enum_values.add()
|
||||||
return {"FINISHED"}
|
return {"FINISHED"}
|
||||||
|
|
||||||
|
|
||||||
@@ -285,6 +366,10 @@ class EditPropTemplate(bpy.types.Operator):
|
|||||||
|
|
||||||
def _execute(self, context):
|
def _execute(self, context):
|
||||||
props = context.scene.BIMPsetTemplateProperties
|
props = context.scene.BIMPsetTemplateProperties
|
||||||
|
if props.active_prop_template.template_type == "P_ENUMERATEDVALUE":
|
||||||
|
enumerator = self.generate_prop_enum(props)
|
||||||
|
else:
|
||||||
|
enumerator = None
|
||||||
ifcopenshell.api.run(
|
ifcopenshell.api.run(
|
||||||
"pset_template.edit_prop_template",
|
"pset_template.edit_prop_template",
|
||||||
IfcStore.pset_template_file,
|
IfcStore.pset_template_file,
|
||||||
@@ -294,12 +379,28 @@ class EditPropTemplate(bpy.types.Operator):
|
|||||||
"Name": props.active_prop_template.name,
|
"Name": props.active_prop_template.name,
|
||||||
"Description": props.active_prop_template.description,
|
"Description": props.active_prop_template.description,
|
||||||
"PrimaryMeasureType": props.active_prop_template.primary_measure_type,
|
"PrimaryMeasureType": props.active_prop_template.primary_measure_type,
|
||||||
|
"TemplateType": props.active_prop_template.template_type,
|
||||||
|
"Enumerators": enumerator
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
Data.load(IfcStore.pset_template_file)
|
Data.load(IfcStore.pset_template_file)
|
||||||
bpy.ops.bim.disable_editing_prop_template()
|
bpy.ops.bim.disable_editing_prop_template()
|
||||||
return {"FINISHED"}
|
return {"FINISHED"}
|
||||||
|
|
||||||
|
#TODO -This will need to go into the
|
||||||
|
# api code at some point - vulevukusej
|
||||||
|
def generate_prop_enum(self, props):
|
||||||
|
self.file = IfcStore.pset_template_file
|
||||||
|
data_type = props.active_prop_template.get_value_name()
|
||||||
|
prop = props.active_prop_template
|
||||||
|
prop_enum = self.file.create_entity(
|
||||||
|
"IFCPROPERTYENUMERATION",
|
||||||
|
Name=prop.name,
|
||||||
|
EnumerationValues=tuple(self.file.create_entity(
|
||||||
|
prop.primary_measure_type, ev[data_type]) for ev in prop.enum_values)
|
||||||
|
)
|
||||||
|
return prop_enum
|
||||||
|
|
||||||
def rollback(self, data):
|
def rollback(self, data):
|
||||||
IfcStore.pset_template_file.undo()
|
IfcStore.pset_template_file.undo()
|
||||||
|
|||||||
@@ -146,16 +146,43 @@ class PsetTemplate(PropertyGroup):
|
|||||||
applicable_entity: StringProperty(name="Applicable Entity")
|
applicable_entity: StringProperty(name="Applicable Entity")
|
||||||
|
|
||||||
|
|
||||||
|
class EnumerationValues(PropertyGroup):
|
||||||
|
string_value: StringProperty(name="Value")
|
||||||
|
bool_value: BoolProperty(name="Value")
|
||||||
|
int_value: IntProperty(name="Value")
|
||||||
|
float_value: FloatProperty(name="Value")
|
||||||
|
|
||||||
|
|
||||||
class PropTemplate(PropertyGroup):
|
class PropTemplate(PropertyGroup):
|
||||||
global_id: StringProperty(name="Global ID")
|
global_id: StringProperty(name="Global ID")
|
||||||
name: StringProperty(name="Name")
|
name: StringProperty(name="Name")
|
||||||
description: StringProperty(name="Description")
|
description: StringProperty(name="Description")
|
||||||
primary_measure_type: EnumProperty(items=get_primary_measure_type, name="Primary Measure Type")
|
primary_measure_type: EnumProperty(items=get_primary_measure_type, name="Primary Measure Type")
|
||||||
|
template_type: EnumProperty(
|
||||||
|
items=[
|
||||||
|
("P_SINGLEVALUE","P_SINGLEVALUE",""),
|
||||||
|
("P_ENUMERATEDVALUE","P_ENUMERATEDVALUE","")
|
||||||
|
],
|
||||||
|
name="Template Type"
|
||||||
|
)
|
||||||
|
enum_values: CollectionProperty(type=EnumerationValues)
|
||||||
getter_enum = {
|
getter_enum = {
|
||||||
"primary_measure_type": get_primary_measure_type,
|
"primary_measure_type": get_primary_measure_type,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
def get_value_name(self):
|
||||||
|
ifc_data_type = IfcStore.get_schema().declaration_by_name(self.primary_measure_type)
|
||||||
|
data_type = ifcopenshell.util.attribute.get_primitive_type(ifc_data_type)
|
||||||
|
if data_type == "string":
|
||||||
|
return "string_value"
|
||||||
|
elif data_type == "boolean":
|
||||||
|
return "bool_value"
|
||||||
|
elif data_type == "integer":
|
||||||
|
return "int_value"
|
||||||
|
elif data_type == "float":
|
||||||
|
return "float_value"
|
||||||
|
|
||||||
|
|
||||||
class BIMPsetTemplateProperties(PropertyGroup):
|
class BIMPsetTemplateProperties(PropertyGroup):
|
||||||
pset_template_files: EnumProperty(
|
pset_template_files: EnumProperty(
|
||||||
@@ -166,7 +193,8 @@ class BIMPsetTemplateProperties(PropertyGroup):
|
|||||||
active_prop_template_id: IntProperty(name="Active Prop Template Id")
|
active_prop_template_id: IntProperty(name="Active Prop Template Id")
|
||||||
active_pset_template: PointerProperty(type=PsetTemplate)
|
active_pset_template: PointerProperty(type=PsetTemplate)
|
||||||
active_prop_template: PointerProperty(type=PropTemplate)
|
active_prop_template: PointerProperty(type=PropTemplate)
|
||||||
|
new_template_filename: StringProperty("New TemplateFileName")
|
||||||
|
|
||||||
getter_enum = {
|
getter_enum = {
|
||||||
"pset_template_files": getPsetTemplateFiles,
|
"pset_template_files": getPsetTemplateFiles,
|
||||||
"pset_templates": getPsetTemplates,
|
"pset_templates": getPsetTemplates,
|
||||||
|
|||||||
@@ -38,11 +38,13 @@ class BIM_PT_pset_template(Panel):
|
|||||||
def draw(self, context):
|
def draw(self, context):
|
||||||
layout = self.layout
|
layout = self.layout
|
||||||
props = context.scene.BIMPsetTemplateProperties
|
props = context.scene.BIMPsetTemplateProperties
|
||||||
|
|
||||||
row = layout.row(align=True)
|
row = layout.row(align=True)
|
||||||
prop_with_search(row, props, "pset_template_files", text="")
|
prop_with_search(row, props, "pset_template_files", text="")
|
||||||
row.operator("bim.save_pset_template_file", text="", icon="EXPORT")
|
row.operator("bim.save_pset_template_file", text="", icon="EXPORT")
|
||||||
|
row.operator("bim.add_pset_file",icon="ADD",text="")
|
||||||
|
row.operator("bim.refresh_psettemplates", icon="FILE_REFRESH", text="")
|
||||||
|
|
||||||
row = layout.row(align=True)
|
row = layout.row(align=True)
|
||||||
|
|
||||||
if bool(getPsetTemplates(props, context)):
|
if bool(getPsetTemplates(props, context)):
|
||||||
@@ -74,7 +76,7 @@ class BIM_PT_pset_template(Panel):
|
|||||||
row.prop(props.active_pset_template, "template_type")
|
row.prop(props.active_pset_template, "template_type")
|
||||||
row = layout.row()
|
row = layout.row()
|
||||||
row.prop(props.active_pset_template, "applicable_entity")
|
row.prop(props.active_pset_template, "applicable_entity")
|
||||||
else:
|
else:
|
||||||
pset_template = Data.pset_templates[int(props.pset_templates)]
|
pset_template = Data.pset_templates[int(props.pset_templates)]
|
||||||
for name, value in pset_template.items():
|
for name, value in pset_template.items():
|
||||||
if name == "id" or name == "type" or name == "HasPropertyTemplates":
|
if name == "id" or name == "type" or name == "HasPropertyTemplates":
|
||||||
@@ -86,6 +88,9 @@ class BIM_PT_pset_template(Panel):
|
|||||||
row = layout.row(align=True)
|
row = layout.row(align=True)
|
||||||
row.label(text="Property Templates", icon="COPY_ID")
|
row.label(text="Property Templates", icon="COPY_ID")
|
||||||
row.operator("bim.add_prop_template", icon="ADD", text="")
|
row.operator("bim.add_prop_template", icon="ADD", text="")
|
||||||
|
|
||||||
|
row = layout.row()
|
||||||
|
row.label(text="Name | Description | PrimaryMeasureType | TemplateType")
|
||||||
|
|
||||||
for prop_template_id in pset_template["HasPropertyTemplates"]:
|
for prop_template_id in pset_template["HasPropertyTemplates"]:
|
||||||
prop_template = Data.prop_templates[prop_template_id]
|
prop_template = Data.prop_templates[prop_template_id]
|
||||||
@@ -95,10 +100,32 @@ class BIM_PT_pset_template(Panel):
|
|||||||
row.prop(props.active_prop_template, "name", text="")
|
row.prop(props.active_prop_template, "name", text="")
|
||||||
row.prop(props.active_prop_template, "description", text="")
|
row.prop(props.active_prop_template, "description", text="")
|
||||||
prop_with_search(row, props.active_prop_template, "primary_measure_type", text="")
|
prop_with_search(row, props.active_prop_template, "primary_measure_type", text="")
|
||||||
|
row.prop(props.active_prop_template, "template_type", text="")
|
||||||
|
|
||||||
|
if props.active_prop_template.template_type == "P_ENUMERATEDVALUE":
|
||||||
|
row = layout.row(align=True)
|
||||||
|
split = row.split(factor=0.2)
|
||||||
|
c=split.column()
|
||||||
|
c.label(text="Enumerations:",)
|
||||||
|
|
||||||
|
c=split.column()
|
||||||
|
box = c.box()
|
||||||
|
grid = box.column_flow(columns=4)
|
||||||
|
value_name = props.active_prop_template.get_value_name()
|
||||||
|
r = grid.row()
|
||||||
|
r.operator("bim.add_prop_enum", text="Add Enum")
|
||||||
|
for k,v in enumerate(props.active_prop_template.enum_values):
|
||||||
|
r = grid.row(align=True)
|
||||||
|
r.prop(v, value_name, text="")
|
||||||
|
op = r.operator("bim.delete_prop_enum", icon="X", text="")
|
||||||
|
op.index = k
|
||||||
|
|
||||||
|
|
||||||
else:
|
else:
|
||||||
row.label(text=prop_template["Name"])
|
row.label(text=prop_template["Name"])
|
||||||
row.label(text=prop_template["Description"])
|
row.label(text=prop_template["Description"])
|
||||||
row.label(text=prop_template["PrimaryMeasureType"])
|
row.label(text=prop_template["PrimaryMeasureType"])
|
||||||
|
row.label(text=prop_template["TemplateType"])
|
||||||
|
|
||||||
if props.active_prop_template_id and props.active_prop_template_id == prop_template_id:
|
if props.active_prop_template_id and props.active_prop_template_id == prop_template_id:
|
||||||
op = row.operator("bim.edit_prop_template", icon="CHECKMARK", text="")
|
op = row.operator("bim.edit_prop_template", icon="CHECKMARK", text="")
|
||||||
|
|||||||
@@ -35,6 +35,7 @@ class Usecase:
|
|||||||
"PrimaryMeasureType": "IfcLabel",
|
"PrimaryMeasureType": "IfcLabel",
|
||||||
"TemplateType": "P_SINGLEVALUE",
|
"TemplateType": "P_SINGLEVALUE",
|
||||||
"AccessState": "READWRITE",
|
"AccessState": "READWRITE",
|
||||||
|
"Enumerators": None
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
has_property_templates = list(self.settings["pset_template"].HasPropertyTemplates or [])
|
has_property_templates = list(self.settings["pset_template"].HasPropertyTemplates or [])
|
||||||
|
|||||||
@@ -49,5 +49,7 @@ class Data:
|
|||||||
"Name": data["Name"],
|
"Name": data["Name"],
|
||||||
"Description": data["Description"],
|
"Description": data["Description"],
|
||||||
"PrimaryMeasureType": data["PrimaryMeasureType"],
|
"PrimaryMeasureType": data["PrimaryMeasureType"],
|
||||||
|
"TemplateType": data["TemplateType"],
|
||||||
|
"Enumerators": data["Enumerators"]
|
||||||
}
|
}
|
||||||
cls.is_loaded = True
|
cls.is_loaded = True
|
||||||
|
|||||||
Reference in New Issue
Block a user