mirror of
https://github.com/IfcOpenShell/IfcOpenShell.git
synced 2026-09-22 11:18:01 +00:00
You can now create new projects starting from a template.
This commit is contained in:
@@ -75,7 +75,7 @@ class BIM_PT_aggregate(Panel):
|
|||||||
row.operator("bim.add_aggregate", icon="ADD", text="")
|
row.operator("bim.add_aggregate", icon="ADD", text="")
|
||||||
|
|
||||||
row = layout.row(align=True)
|
row = layout.row(align=True)
|
||||||
parts = AggregateData.data['related_objects_amount']
|
parts = AggregateData.data["related_objects_amount"]
|
||||||
row.label(text=f"{parts or 'No'} Part{'s' if parts > 1 else ''}", icon="TRIA_DOWN")
|
row.label(text=f"{parts or 'No'} Part{'s' if parts > 1 else ''}", icon="TRIA_DOWN")
|
||||||
if AggregateData.data["has_related_objects"]:
|
if AggregateData.data["has_related_objects"]:
|
||||||
op = row.operator("bim.select_parts", icon="RESTRICT_SELECT_OFF", text="")
|
op = row.operator("bim.select_parts", icon="RESTRICT_SELECT_OFF", text="")
|
||||||
|
|||||||
@@ -16,6 +16,7 @@
|
|||||||
# 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 blenderbim.tool as tool
|
import blenderbim.tool as tool
|
||||||
from blenderbim.bim.ifc import IfcStore
|
from blenderbim.bim.ifc import IfcStore
|
||||||
@@ -31,9 +32,16 @@ class ProjectData:
|
|||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
def load(cls):
|
def load(cls):
|
||||||
cls.data = {"export_schema": cls.get_export_schema()}
|
cls.data = {"export_schema": cls.get_export_schema(), "template_file": cls.template_file()}
|
||||||
cls.is_loaded = True
|
cls.is_loaded = True
|
||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
def get_export_schema(cls):
|
def get_export_schema(cls):
|
||||||
return [(s, s, "") for s in IfcStore.schema_identifiers]
|
return [(s, s, "") for s in IfcStore.schema_identifiers]
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def template_file(cls):
|
||||||
|
files = os.listdir(os.path.join(bpy.context.scene.BIMProperties.data_dir, "libraries"))
|
||||||
|
results = [("0", "Blank Project", "")]
|
||||||
|
results.extend([(f, f.replace(".ifc", ""), "") for f in files if ".ifc" in f])
|
||||||
|
return results
|
||||||
|
|||||||
@@ -27,6 +27,7 @@ import ifcopenshell.util.selector
|
|||||||
import ifcopenshell.util.representation
|
import ifcopenshell.util.representation
|
||||||
import blenderbim.bim.handler
|
import blenderbim.bim.handler
|
||||||
import blenderbim.tool as tool
|
import blenderbim.tool as tool
|
||||||
|
import blenderbim.core.project as core
|
||||||
import blenderbim.core.context
|
import blenderbim.core.context
|
||||||
import blenderbim.core.owner
|
import blenderbim.core.owner
|
||||||
from blenderbim.bim.ifc import IfcStore
|
from blenderbim.bim.ifc import IfcStore
|
||||||
@@ -45,80 +46,16 @@ class CreateProject(bpy.types.Operator):
|
|||||||
def execute(self, context):
|
def execute(self, context):
|
||||||
IfcStore.begin_transaction(self)
|
IfcStore.begin_transaction(self)
|
||||||
IfcStore.add_transaction_operation(self, rollback=self.rollback, commit=lambda data: True)
|
IfcStore.add_transaction_operation(self, rollback=self.rollback, commit=lambda data: True)
|
||||||
result = self._execute(context)
|
self._execute(context)
|
||||||
self.transaction_data = {"file": self.file}
|
self.transaction_data = {"file": tool.Ifc.get()}
|
||||||
IfcStore.add_transaction_operation(self, rollback=lambda data: True, commit=self.commit)
|
IfcStore.add_transaction_operation(self, rollback=lambda data: True, commit=self.commit)
|
||||||
IfcStore.end_transaction(self)
|
IfcStore.end_transaction(self)
|
||||||
return result
|
|
||||||
|
|
||||||
def _execute(self, context):
|
|
||||||
active_object = context.view_layer.objects.active
|
|
||||||
self.file = IfcStore.get_file()
|
|
||||||
if self.file:
|
|
||||||
return {"FINISHED"}
|
|
||||||
|
|
||||||
IfcStore.file = ifcopenshell.api.run(
|
|
||||||
"project.create_file", **{"version": context.scene.BIMProjectProperties.export_schema}
|
|
||||||
)
|
|
||||||
self.file = IfcStore.get_file()
|
|
||||||
|
|
||||||
if self.file.schema == "IFC2X3":
|
|
||||||
person = blenderbim.core.owner.add_person(tool.Ifc)
|
|
||||||
organisation = blenderbim.core.owner.add_organisation(tool.Ifc)
|
|
||||||
user = blenderbim.core.owner.add_person_and_organisation(tool.Ifc, person=person, organisation=organisation)
|
|
||||||
blenderbim.core.owner.set_user(tool.Owner, user=user)
|
|
||||||
|
|
||||||
project = bpy.data.objects.new(self.get_name("IfcProject", "My Project"), None)
|
|
||||||
site = bpy.data.objects.new(self.get_name("IfcSite", "My Site"), None)
|
|
||||||
building = bpy.data.objects.new(self.get_name("IfcBuilding", "My Building"), None)
|
|
||||||
building_storey = bpy.data.objects.new(self.get_name("IfcBuildingStorey", "My Storey"), None)
|
|
||||||
|
|
||||||
bpy.ops.bim.assign_class(obj=project.name, ifc_class="IfcProject")
|
|
||||||
blenderbim.core.unit.assign_scene_units(tool.Ifc, tool.Unit)
|
|
||||||
|
|
||||||
model = blenderbim.core.context.add_context(
|
|
||||||
tool.Ifc, context_type="Model", context_identifier="", target_view="", parent=0
|
|
||||||
)
|
|
||||||
body_context = blenderbim.core.context.add_context(
|
|
||||||
tool.Ifc, context_type="Model", context_identifier="Body", target_view="MODEL_VIEW", parent=model
|
|
||||||
)
|
|
||||||
blenderbim.core.context.add_context(
|
|
||||||
tool.Ifc, context_type="Model", context_identifier="Box", target_view="MODEL_VIEW", parent=model
|
|
||||||
)
|
|
||||||
plan = blenderbim.core.context.add_context(
|
|
||||||
tool.Ifc, context_type="Plan", context_identifier="", target_view="", parent=0
|
|
||||||
)
|
|
||||||
blenderbim.core.context.add_context(
|
|
||||||
tool.Ifc, context_type="Plan", context_identifier="Annotation", target_view="PLAN_VIEW", parent=plan
|
|
||||||
)
|
|
||||||
|
|
||||||
blenderbim.bim.handler.refresh_ui_data()
|
|
||||||
context.scene.BIMRootProperties.contexts = str(body_context.id())
|
|
||||||
|
|
||||||
bpy.ops.bim.assign_class(obj=site.name, ifc_class="IfcSite")
|
|
||||||
bpy.ops.bim.assign_class(obj=building.name, ifc_class="IfcBuilding")
|
|
||||||
bpy.ops.bim.assign_class(obj=building_storey.name, ifc_class="IfcBuildingStorey")
|
|
||||||
|
|
||||||
blenderbim.core.aggregate.assign_object(
|
|
||||||
tool.Ifc, tool.Aggregate, tool.Collector, relating_obj=project, related_obj=site
|
|
||||||
)
|
|
||||||
blenderbim.core.aggregate.assign_object(
|
|
||||||
tool.Ifc, tool.Aggregate, tool.Collector, relating_obj=site, related_obj=building
|
|
||||||
)
|
|
||||||
blenderbim.core.aggregate.assign_object(
|
|
||||||
tool.Ifc, tool.Aggregate, tool.Collector, relating_obj=building, related_obj=building_storey
|
|
||||||
)
|
|
||||||
|
|
||||||
context.view_layer.objects.active = active_object
|
|
||||||
return {"FINISHED"}
|
return {"FINISHED"}
|
||||||
|
|
||||||
def get_name(self, ifc_class, name):
|
def _execute(self, context):
|
||||||
if not bpy.data.objects.get(f"{ifc_class}/{name}"):
|
props = context.scene.BIMProjectProperties
|
||||||
return name
|
template = None if props.template_file == "0" else props.template_file
|
||||||
i = 2
|
core.create_project(tool.Ifc, tool.Project, schema=props.export_schema, template=template)
|
||||||
while bpy.data.objects.get(f"{ifc_class}/{name} {i}"):
|
|
||||||
i += 1
|
|
||||||
return f"{name} {i}"
|
|
||||||
|
|
||||||
def rollback(self, data):
|
def rollback(self, data):
|
||||||
IfcStore.file = None
|
IfcStore.file = None
|
||||||
@@ -373,7 +310,11 @@ class AppendLibraryElement(bpy.types.Operator):
|
|||||||
self.import_type_from_ifc(element, context)
|
self.import_type_from_ifc(element, context)
|
||||||
elif element.is_a("IfcMaterial"):
|
elif element.is_a("IfcMaterial"):
|
||||||
self.import_material_from_ifc(element, context)
|
self.import_material_from_ifc(element, context)
|
||||||
context.scene.BIMProjectProperties.library_elements[self.prop_index].is_appended = True
|
try:
|
||||||
|
context.scene.BIMProjectProperties.library_elements[self.prop_index].is_appended = True
|
||||||
|
except:
|
||||||
|
# TODO Remove this terrible code when I refactor this into the core
|
||||||
|
pass
|
||||||
blenderbim.bim.handler.purge_module_data()
|
blenderbim.bim.handler.purge_module_data()
|
||||||
return {"FINISHED"}
|
return {"FINISHED"}
|
||||||
|
|
||||||
|
|||||||
@@ -38,6 +38,12 @@ def get_export_schema(self, context):
|
|||||||
return ProjectData.data["export_schema"]
|
return ProjectData.data["export_schema"]
|
||||||
|
|
||||||
|
|
||||||
|
def get_template_file(self, context):
|
||||||
|
if not ProjectData.is_loaded:
|
||||||
|
ProjectData.load()
|
||||||
|
return ProjectData.data["template_file"]
|
||||||
|
|
||||||
|
|
||||||
def update_filter_mode(self, context):
|
def update_filter_mode(self, context):
|
||||||
self.filter_categories.clear()
|
self.filter_categories.clear()
|
||||||
if self.filter_mode == "NONE":
|
if self.filter_mode == "NONE":
|
||||||
@@ -132,6 +138,7 @@ class BIMProjectProperties(PropertyGroup):
|
|||||||
links: CollectionProperty(name="Links", type=Link)
|
links: CollectionProperty(name="Links", type=Link)
|
||||||
active_link_index: IntProperty(name="Active Link Index")
|
active_link_index: IntProperty(name="Active Link Index")
|
||||||
export_schema: EnumProperty(items=get_export_schema, name="IFC Schema")
|
export_schema: EnumProperty(items=get_export_schema, name="IFC Schema")
|
||||||
|
template_file: EnumProperty(items=get_template_file, name="Template File")
|
||||||
|
|
||||||
def get_library_element_index(self, lib_element):
|
def get_library_element_index(self, lib_element):
|
||||||
return next((i for i in range(len(self.library_elements)) if self.library_elements[i] == lib_element))
|
return next((i for i in range(len(self.library_elements)) if self.library_elements[i] == lib_element))
|
||||||
|
|||||||
@@ -156,6 +156,9 @@ class BIM_PT_project(Panel):
|
|||||||
row.prop(props, "area_unit", text="Area Unit")
|
row.prop(props, "area_unit", text="Area Unit")
|
||||||
row = self.layout.row()
|
row = self.layout.row()
|
||||||
row.prop(props, "volume_unit", text="Volume Unit")
|
row.prop(props, "volume_unit", text="Volume Unit")
|
||||||
|
row = self.layout.row()
|
||||||
|
row.prop(pprops, "template_file", text="Template")
|
||||||
|
|
||||||
row = self.layout.row(align=True)
|
row = self.layout.row(align=True)
|
||||||
row.operator("bim.create_project")
|
row.operator("bim.create_project")
|
||||||
row.operator("bim.load_project")
|
row.operator("bim.load_project")
|
||||||
|
|||||||
@@ -0,0 +1,63 @@
|
|||||||
|
# BlenderBIM Add-on - OpenBIM Blender Add-on
|
||||||
|
# Copyright (C) 2022 Dion Moult <dion@thinkmoult.com>
|
||||||
|
#
|
||||||
|
# This file is part of BlenderBIM Add-on.
|
||||||
|
#
|
||||||
|
# BlenderBIM Add-on is free software: you can redistribute it and/or modify
|
||||||
|
# it under the terms of the GNU General Public License as published by
|
||||||
|
# the Free Software Foundation, either version 3 of the License, or
|
||||||
|
# (at your option) any later version.
|
||||||
|
#
|
||||||
|
# BlenderBIM Add-on is distributed in the hope that it will be useful,
|
||||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
# GNU General Public License for more details.
|
||||||
|
#
|
||||||
|
# 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/>.
|
||||||
|
|
||||||
|
|
||||||
|
def create_project(ifc, project, schema=None, template=None):
|
||||||
|
if ifc.get():
|
||||||
|
return
|
||||||
|
|
||||||
|
ifc.set(ifc.run("project.create_file", version=schema))
|
||||||
|
|
||||||
|
if schema == "IFC2X3":
|
||||||
|
person = project.run_owner_add_person()
|
||||||
|
organisation = project.run_owner_add_organisation()
|
||||||
|
user = project.run_owner_add_person_and_organisation(person=person, organisation=organisation)
|
||||||
|
project.run_owner_set_user(user=user)
|
||||||
|
|
||||||
|
project_obj = project.create_empty("My Project")
|
||||||
|
site = project.create_empty("My Site")
|
||||||
|
building = project.create_empty("My Building")
|
||||||
|
storey = project.create_empty("My Storey")
|
||||||
|
|
||||||
|
project.run_root_assign_class(obj=project_obj, ifc_class="IfcProject")
|
||||||
|
project.run_unit_assign_scene_units()
|
||||||
|
|
||||||
|
model = project.run_context_add_context(context_type="Model", context_identifier="", target_view="", parent=0)
|
||||||
|
body = project.run_context_add_context(
|
||||||
|
context_type="Model", context_identifier="Body", target_view="MODEL_VIEW", parent=model
|
||||||
|
)
|
||||||
|
project.run_context_add_context(
|
||||||
|
context_type="Model", context_identifier="Box", target_view="MODEL_VIEW", parent=model
|
||||||
|
)
|
||||||
|
plan = project.run_context_add_context(context_type="Plan", context_identifier="", target_view="", parent=0)
|
||||||
|
annotation = project.run_context_add_context(
|
||||||
|
context_type="Plan", context_identifier="Annotation", target_view="PLAN_VIEW", parent=plan
|
||||||
|
)
|
||||||
|
|
||||||
|
project.run_root_assign_class(obj=site, ifc_class="IfcSite", context=body)
|
||||||
|
project.run_root_assign_class(obj=building, ifc_class="IfcBuilding", context=body)
|
||||||
|
project.run_root_assign_class(obj=storey, ifc_class="IfcBuildingStorey", context=body)
|
||||||
|
|
||||||
|
project.run_aggregate_assign_object(relating_obj=project_obj, related_obj=site)
|
||||||
|
project.run_aggregate_assign_object(relating_obj=site, related_obj=building)
|
||||||
|
project.run_aggregate_assign_object(relating_obj=building, related_obj=storey)
|
||||||
|
|
||||||
|
project.set_context(body)
|
||||||
|
|
||||||
|
if template:
|
||||||
|
project.append_all_types_from_template(template)
|
||||||
@@ -215,6 +215,7 @@ class Ifc:
|
|||||||
def get_schema(cls): pass
|
def get_schema(cls): pass
|
||||||
def link(cls, element, obj): pass
|
def link(cls, element, obj): pass
|
||||||
def run(cls, command, **kwargs): pass
|
def run(cls, command, **kwargs): pass
|
||||||
|
def set(cls, ifc): pass
|
||||||
def unlink(cls, element=None, obj=None): pass
|
def unlink(cls, element=None, obj=None): pass
|
||||||
|
|
||||||
|
|
||||||
@@ -292,6 +293,21 @@ class Owner:
|
|||||||
def set_user(cls, user): pass
|
def set_user(cls, user): pass
|
||||||
|
|
||||||
|
|
||||||
|
@interface
|
||||||
|
class Project:
|
||||||
|
def append_all_types_from_template(cls, template): pass
|
||||||
|
def create_empty(cls, name): pass
|
||||||
|
def run_aggregate_assign_object(cls, relating_obj=None, related_obj=None): pass
|
||||||
|
def run_context_add_context(cls, context_type=None, context_identifier=None, target_view=None, parent=None): pass
|
||||||
|
def run_owner_add_organisation(cls): pass
|
||||||
|
def run_owner_add_person(cls): pass
|
||||||
|
def run_owner_add_person_and_organisation(cls, person=None, organisation=None): pass
|
||||||
|
def run_owner_set_user(cls, user=None): pass
|
||||||
|
def run_root_assign_class(cls, obj=None, ifc_class=None, predefined_type=None, should_add_representation=True, context=None, ifc_representation_class=None): pass
|
||||||
|
def run_unit_assign_scene_units(cls): pass
|
||||||
|
def set_context(cls, context): pass
|
||||||
|
|
||||||
|
|
||||||
@interface
|
@interface
|
||||||
class Pset:
|
class Pset:
|
||||||
def get_element_pset(cls, element, pset_name): pass
|
def get_element_pset(cls, element, pset_name): pass
|
||||||
|
|||||||
@@ -33,6 +33,7 @@ from blenderbim.tool.misc import Misc
|
|||||||
from blenderbim.tool.model import Model
|
from blenderbim.tool.model import Model
|
||||||
from blenderbim.tool.owner import Owner
|
from blenderbim.tool.owner import Owner
|
||||||
from blenderbim.tool.patch import Patch
|
from blenderbim.tool.patch import Patch
|
||||||
|
from blenderbim.tool.project import Project
|
||||||
from blenderbim.tool.pset import Pset
|
from blenderbim.tool.pset import Pset
|
||||||
from blenderbim.tool.qto import Qto
|
from blenderbim.tool.qto import Qto
|
||||||
from blenderbim.tool.root import Root
|
from blenderbim.tool.root import Root
|
||||||
|
|||||||
@@ -0,0 +1,100 @@
|
|||||||
|
# BlenderBIM Add-on - OpenBIM Blender Add-on
|
||||||
|
# Copyright (C) 2022 Dion Moult <dion@thinkmoult.com>
|
||||||
|
#
|
||||||
|
# This file is part of BlenderBIM Add-on.
|
||||||
|
#
|
||||||
|
# BlenderBIM Add-on is free software: you can redistribute it and/or modify
|
||||||
|
# it under the terms of the GNU General Public License as published by
|
||||||
|
# the Free Software Foundation, either version 3 of the License, or
|
||||||
|
# (at your option) any later version.
|
||||||
|
#
|
||||||
|
# BlenderBIM Add-on is distributed in the hope that it will be useful,
|
||||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
# GNU General Public License for more details.
|
||||||
|
#
|
||||||
|
# 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/>.
|
||||||
|
|
||||||
|
import os
|
||||||
|
import bpy
|
||||||
|
import blenderbim.core.tool
|
||||||
|
import blenderbim.tool as tool
|
||||||
|
from blenderbim.bim.ifc import IfcStore
|
||||||
|
|
||||||
|
|
||||||
|
class Project(blenderbim.core.tool.Project):
|
||||||
|
@classmethod
|
||||||
|
def append_all_types_from_template(cls, template):
|
||||||
|
# TODO refactor
|
||||||
|
filepath = os.path.join(bpy.context.scene.BIMProperties.data_dir, "libraries", template)
|
||||||
|
bpy.ops.bim.select_library_file(filepath=filepath)
|
||||||
|
for element in IfcStore.library_file.by_type("IfcTypeProduct"):
|
||||||
|
bpy.ops.bim.append_library_element(definition=element.id())
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def create_empty(cls, name):
|
||||||
|
return bpy.data.objects.new(name, None)
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def run_aggregate_assign_object(cls, relating_obj=None, related_obj=None):
|
||||||
|
return blenderbim.core.aggregate.assign_object(
|
||||||
|
tool.Ifc, tool.Aggregate, tool.Collector, relating_obj=relating_obj, related_obj=related_obj
|
||||||
|
)
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def run_context_add_context(cls, context_type=None, context_identifier=None, target_view=None, parent=None):
|
||||||
|
return blenderbim.core.context.add_context(
|
||||||
|
tool.Ifc,
|
||||||
|
context_type=context_type,
|
||||||
|
context_identifier=context_identifier,
|
||||||
|
target_view=target_view,
|
||||||
|
parent=parent,
|
||||||
|
)
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def run_owner_add_organisation(cls):
|
||||||
|
return blenderbim.core.owner.add_organisation(tool.Ifc)
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def run_owner_add_person(cls):
|
||||||
|
return blenderbim.core.owner.add_person(tool.Ifc)
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def run_owner_add_person_and_organisation(cls, person=None, organisation=None):
|
||||||
|
return blenderbim.core.owner.add_person_and_organisation(tool.Ifc, person=person, organisation=organisation)
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def run_owner_set_user(cls, user=None):
|
||||||
|
return blenderbim.core.owner.set_user(tool.Owner, user=user)
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def run_root_assign_class(
|
||||||
|
cls,
|
||||||
|
obj=None,
|
||||||
|
ifc_class=None,
|
||||||
|
predefined_type=None,
|
||||||
|
should_add_representation=True,
|
||||||
|
context=None,
|
||||||
|
ifc_representation_class=None,
|
||||||
|
):
|
||||||
|
return blenderbim.core.root.assign_class(
|
||||||
|
tool.Ifc,
|
||||||
|
tool.Collector,
|
||||||
|
tool.Root,
|
||||||
|
obj=obj,
|
||||||
|
ifc_class=ifc_class,
|
||||||
|
predefined_type=predefined_type,
|
||||||
|
should_add_representation=should_add_representation,
|
||||||
|
context=context,
|
||||||
|
ifc_representation_class=ifc_representation_class,
|
||||||
|
)
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def run_unit_assign_scene_units(cls):
|
||||||
|
return blenderbim.core.unit.assign_scene_units(tool.Ifc, tool.Unit)
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def set_context(cls, context):
|
||||||
|
blenderbim.bim.handler.refresh_ui_data()
|
||||||
|
bpy.context.scene.BIMRootProperties.contexts = str(context.id())
|
||||||
@@ -126,6 +126,13 @@ def patch():
|
|||||||
prophet.verify()
|
prophet.verify()
|
||||||
|
|
||||||
|
|
||||||
|
@pytest.fixture
|
||||||
|
def project():
|
||||||
|
prophet = Prophecy(blenderbim.core.tool.Project)
|
||||||
|
yield prophet
|
||||||
|
prophet.verify()
|
||||||
|
|
||||||
|
|
||||||
@pytest.fixture
|
@pytest.fixture
|
||||||
def pset():
|
def pset():
|
||||||
prophet = Prophecy(blenderbim.core.tool.Pset)
|
prophet = Prophecy(blenderbim.core.tool.Pset)
|
||||||
|
|||||||
@@ -0,0 +1,156 @@
|
|||||||
|
# BlenderBIM Add-on - OpenBIM Blender Add-on
|
||||||
|
# Copyright (C) 2022 Dion Moult <dion@thinkmoult.com>
|
||||||
|
#
|
||||||
|
# This file is part of BlenderBIM Add-on.
|
||||||
|
#
|
||||||
|
# BlenderBIM Add-on is free software: you can redistribute it and/or modify
|
||||||
|
# it under the terms of the GNU General Public License as published by
|
||||||
|
# the Free Software Foundation, either version 3 of the License, or
|
||||||
|
# (at your option) any later version.
|
||||||
|
#
|
||||||
|
# BlenderBIM Add-on is distributed in the hope that it will be useful,
|
||||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
# GNU General Public License for more details.
|
||||||
|
#
|
||||||
|
# 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/>.
|
||||||
|
|
||||||
|
|
||||||
|
import blenderbim.core.project as subject
|
||||||
|
from test.core.bootstrap import ifc, project
|
||||||
|
|
||||||
|
|
||||||
|
class TestCreateProject:
|
||||||
|
def test_do_nothing_if_a_project_already_exists(self, ifc, project):
|
||||||
|
ifc.get().should_be_called().will_return("ifc")
|
||||||
|
subject.create_project(ifc, project, schema="IFC4", template=None)
|
||||||
|
|
||||||
|
def test_create_an_ifc4_project(self, ifc, project):
|
||||||
|
ifc.get().should_be_called().will_return(None)
|
||||||
|
ifc.run("project.create_file", version="IFC4").should_be_called().will_return("ifc")
|
||||||
|
ifc.set("ifc").should_be_called()
|
||||||
|
|
||||||
|
project.create_empty("My Project").should_be_called().will_return("project")
|
||||||
|
project.create_empty("My Site").should_be_called().will_return("site")
|
||||||
|
project.create_empty("My Building").should_be_called().will_return("building")
|
||||||
|
project.create_empty("My Storey").should_be_called().will_return("storey")
|
||||||
|
project.run_root_assign_class(obj="project", ifc_class="IfcProject").should_be_called()
|
||||||
|
project.run_unit_assign_scene_units().should_be_called()
|
||||||
|
|
||||||
|
project.run_context_add_context(
|
||||||
|
context_type="Model", context_identifier="", target_view="", parent=0
|
||||||
|
).should_be_called().will_return("model")
|
||||||
|
project.run_context_add_context(
|
||||||
|
context_type="Model", context_identifier="Body", target_view="MODEL_VIEW", parent="model"
|
||||||
|
).should_be_called().will_return("body")
|
||||||
|
project.run_context_add_context(
|
||||||
|
context_type="Model", context_identifier="Box", target_view="MODEL_VIEW", parent="model"
|
||||||
|
).should_be_called()
|
||||||
|
project.run_context_add_context(
|
||||||
|
context_type="Plan", context_identifier="", target_view="", parent=0
|
||||||
|
).should_be_called().will_return("plan")
|
||||||
|
project.run_context_add_context(
|
||||||
|
context_type="Plan", context_identifier="Annotation", target_view="PLAN_VIEW", parent="plan"
|
||||||
|
).should_be_called()
|
||||||
|
|
||||||
|
project.run_root_assign_class(obj="site", ifc_class="IfcSite", context="body").should_be_called()
|
||||||
|
project.run_root_assign_class(obj="building", ifc_class="IfcBuilding", context="body").should_be_called()
|
||||||
|
project.run_root_assign_class(obj="storey", ifc_class="IfcBuildingStorey", context="body").should_be_called()
|
||||||
|
|
||||||
|
project.run_aggregate_assign_object(relating_obj="project", related_obj="site").should_be_called()
|
||||||
|
project.run_aggregate_assign_object(relating_obj="site", related_obj="building").should_be_called()
|
||||||
|
project.run_aggregate_assign_object(relating_obj="building", related_obj="storey").should_be_called()
|
||||||
|
|
||||||
|
project.set_context("body").should_be_called()
|
||||||
|
|
||||||
|
subject.create_project(ifc, project, schema="IFC4", template=None)
|
||||||
|
|
||||||
|
def test_appending_project_template_types_if_specified(self, ifc, project):
|
||||||
|
ifc.get().should_be_called().will_return(None)
|
||||||
|
ifc.run("project.create_file", version="IFC4").should_be_called().will_return("ifc")
|
||||||
|
ifc.set("ifc").should_be_called()
|
||||||
|
|
||||||
|
project.create_empty("My Project").should_be_called().will_return("project")
|
||||||
|
project.create_empty("My Site").should_be_called().will_return("site")
|
||||||
|
project.create_empty("My Building").should_be_called().will_return("building")
|
||||||
|
project.create_empty("My Storey").should_be_called().will_return("storey")
|
||||||
|
project.run_root_assign_class(obj="project", ifc_class="IfcProject").should_be_called()
|
||||||
|
project.run_unit_assign_scene_units().should_be_called()
|
||||||
|
|
||||||
|
project.run_context_add_context(
|
||||||
|
context_type="Model", context_identifier="", target_view="", parent=0
|
||||||
|
).should_be_called().will_return("model")
|
||||||
|
project.run_context_add_context(
|
||||||
|
context_type="Model", context_identifier="Body", target_view="MODEL_VIEW", parent="model"
|
||||||
|
).should_be_called().will_return("body")
|
||||||
|
project.run_context_add_context(
|
||||||
|
context_type="Model", context_identifier="Box", target_view="MODEL_VIEW", parent="model"
|
||||||
|
).should_be_called()
|
||||||
|
project.run_context_add_context(
|
||||||
|
context_type="Plan", context_identifier="", target_view="", parent=0
|
||||||
|
).should_be_called().will_return("plan")
|
||||||
|
project.run_context_add_context(
|
||||||
|
context_type="Plan", context_identifier="Annotation", target_view="PLAN_VIEW", parent="plan"
|
||||||
|
).should_be_called()
|
||||||
|
|
||||||
|
project.run_root_assign_class(obj="site", ifc_class="IfcSite", context="body").should_be_called()
|
||||||
|
project.run_root_assign_class(obj="building", ifc_class="IfcBuilding", context="body").should_be_called()
|
||||||
|
project.run_root_assign_class(obj="storey", ifc_class="IfcBuildingStorey", context="body").should_be_called()
|
||||||
|
|
||||||
|
project.run_aggregate_assign_object(relating_obj="project", related_obj="site").should_be_called()
|
||||||
|
project.run_aggregate_assign_object(relating_obj="site", related_obj="building").should_be_called()
|
||||||
|
project.run_aggregate_assign_object(relating_obj="building", related_obj="storey").should_be_called()
|
||||||
|
|
||||||
|
project.set_context("body").should_be_called()
|
||||||
|
|
||||||
|
project.append_all_types_from_template("template").should_be_called()
|
||||||
|
|
||||||
|
subject.create_project(ifc, project, schema="IFC4", template="template")
|
||||||
|
|
||||||
|
def test_create_an_ifc2x3_project_with_owner_defaults(self, ifc, project):
|
||||||
|
ifc.get().should_be_called().will_return(None)
|
||||||
|
ifc.run("project.create_file", version="IFC2X3").should_be_called().will_return("ifc")
|
||||||
|
ifc.set("ifc").should_be_called()
|
||||||
|
|
||||||
|
project.run_owner_add_person().should_be_called().will_return("person")
|
||||||
|
project.run_owner_add_organisation().should_be_called().will_return("organisation")
|
||||||
|
project.run_owner_add_person_and_organisation(
|
||||||
|
person="person", organisation="organisation"
|
||||||
|
).should_be_called().will_return("user")
|
||||||
|
project.run_owner_set_user(user="user").should_be_called()
|
||||||
|
|
||||||
|
project.create_empty("My Project").should_be_called().will_return("project")
|
||||||
|
project.create_empty("My Site").should_be_called().will_return("site")
|
||||||
|
project.create_empty("My Building").should_be_called().will_return("building")
|
||||||
|
project.create_empty("My Storey").should_be_called().will_return("storey")
|
||||||
|
project.run_root_assign_class(obj="project", ifc_class="IfcProject").should_be_called()
|
||||||
|
project.run_unit_assign_scene_units().should_be_called()
|
||||||
|
|
||||||
|
project.run_context_add_context(
|
||||||
|
context_type="Model", context_identifier="", target_view="", parent=0
|
||||||
|
).should_be_called().will_return("model")
|
||||||
|
project.run_context_add_context(
|
||||||
|
context_type="Model", context_identifier="Body", target_view="MODEL_VIEW", parent="model"
|
||||||
|
).should_be_called().will_return("body")
|
||||||
|
project.run_context_add_context(
|
||||||
|
context_type="Model", context_identifier="Box", target_view="MODEL_VIEW", parent="model"
|
||||||
|
).should_be_called()
|
||||||
|
project.run_context_add_context(
|
||||||
|
context_type="Plan", context_identifier="", target_view="", parent=0
|
||||||
|
).should_be_called().will_return("plan")
|
||||||
|
project.run_context_add_context(
|
||||||
|
context_type="Plan", context_identifier="Annotation", target_view="PLAN_VIEW", parent="plan"
|
||||||
|
).should_be_called()
|
||||||
|
|
||||||
|
project.run_root_assign_class(obj="site", ifc_class="IfcSite", context="body").should_be_called()
|
||||||
|
project.run_root_assign_class(obj="building", ifc_class="IfcBuilding", context="body").should_be_called()
|
||||||
|
project.run_root_assign_class(obj="storey", ifc_class="IfcBuildingStorey", context="body").should_be_called()
|
||||||
|
|
||||||
|
project.run_aggregate_assign_object(relating_obj="project", related_obj="site").should_be_called()
|
||||||
|
project.run_aggregate_assign_object(relating_obj="site", related_obj="building").should_be_called()
|
||||||
|
project.run_aggregate_assign_object(relating_obj="building", related_obj="storey").should_be_called()
|
||||||
|
|
||||||
|
project.set_context("body").should_be_called()
|
||||||
|
|
||||||
|
subject.create_project(ifc, project, schema="IFC2X3", template=None)
|
||||||
@@ -0,0 +1,91 @@
|
|||||||
|
# BlenderBIM Add-on - OpenBIM Blender Add-on
|
||||||
|
# Copyright (C) 2021 Dion Moult <dion@thinkmoult.com>
|
||||||
|
#
|
||||||
|
# This file is part of BlenderBIM Add-on.
|
||||||
|
#
|
||||||
|
# BlenderBIM Add-on is free software: you can redistribute it and/or modify
|
||||||
|
# it under the terms of the GNU General Public License as published by
|
||||||
|
# the Free Software Foundation, either version 3 of the License, or
|
||||||
|
# (at your option) any later version.
|
||||||
|
#
|
||||||
|
# BlenderBIM Add-on is distributed in the hope that it will be useful,
|
||||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
# GNU General Public License for more details.
|
||||||
|
#
|
||||||
|
# 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/>.
|
||||||
|
|
||||||
|
import bpy
|
||||||
|
import ifcopenshell
|
||||||
|
import blenderbim.core.tool
|
||||||
|
import blenderbim.tool as tool
|
||||||
|
from test.bim.bootstrap import NewFile
|
||||||
|
from blenderbim.tool.project import Project as subject
|
||||||
|
|
||||||
|
|
||||||
|
class TestImplementsTool(NewFile):
|
||||||
|
def test_run(self):
|
||||||
|
assert isinstance(subject(), blenderbim.core.tool.Project)
|
||||||
|
|
||||||
|
|
||||||
|
class TestAppendAllTypesFromTemplate(NewFile):
|
||||||
|
def test_nothing(self):
|
||||||
|
# TODO refactor
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
class TestCreateEmpty(NewFile):
|
||||||
|
def test_run(self):
|
||||||
|
subject.create_empty("Foobar")
|
||||||
|
assert bpy.data.objects.get("Foobar")
|
||||||
|
assert not bpy.data.objects.get("Foobar").data
|
||||||
|
|
||||||
|
|
||||||
|
class TestRunAggregateAssignObject(NewFile):
|
||||||
|
def test_nothing(self):
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
class TestRunContextAddContext(NewFile):
|
||||||
|
def test_nothing(self):
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
class TestRunOwnerAddOrganisation(NewFile):
|
||||||
|
def test_nothing(self):
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
class TestRunOwnerAddPerson(NewFile):
|
||||||
|
def test_nothing(self):
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
class TestRunOwnerAddPersonAndOrganisation(NewFile):
|
||||||
|
def test_nothing(self):
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
class TestRunOwnerSetUser(NewFile):
|
||||||
|
def test_nothing(self):
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
class TestRunAssignClass(NewFile):
|
||||||
|
def test_nothing(self):
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
class TestRunUnitAssignSceneUnits(NewFile):
|
||||||
|
def test_nothing(self):
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
class TestSetContext(NewFile):
|
||||||
|
def test_run(self):
|
||||||
|
ifc = ifcopenshell.file()
|
||||||
|
tool.Ifc.set(ifc)
|
||||||
|
context = ifc.createIfcGeometricRepresentationContext()
|
||||||
|
subject.set_context(context)
|
||||||
|
assert bpy.context.scene.BIMRootProperties.contexts == str(context.id())
|
||||||
Reference in New Issue
Block a user