mirror of
https://github.com/IfcOpenShell/IfcOpenShell.git
synced 2026-08-09 09:21:46 +00:00
Implement undo for pset template operators. See #1475.
This commit is contained in:
@@ -124,6 +124,7 @@ def undo_post(scene):
|
||||
if IfcStore.last_transaction != bpy.context.scene.BIMProperties.last_transaction:
|
||||
IfcStore.last_transaction = bpy.context.scene.BIMProperties.last_transaction
|
||||
IfcStore.undo()
|
||||
purge_module_data()
|
||||
IfcStore.update_undo_redo_stack_objects()
|
||||
IfcStore.reload_linked_elements(objects=[bpy.data.objects.get(o) for o in IfcStore.undo_redo_stack_objects])
|
||||
|
||||
@@ -138,6 +139,7 @@ def redo_post(scene):
|
||||
if IfcStore.last_transaction != bpy.context.scene.BIMProperties.last_transaction:
|
||||
IfcStore.last_transaction = bpy.context.scene.BIMProperties.last_transaction
|
||||
IfcStore.redo()
|
||||
purge_module_data()
|
||||
IfcStore.update_undo_redo_stack_objects()
|
||||
IfcStore.reload_linked_elements(objects=[bpy.data.objects.get(o) for o in IfcStore.undo_redo_stack_objects])
|
||||
|
||||
|
||||
@@ -71,19 +71,19 @@ class IfcStore:
|
||||
def add_element_listener(callback):
|
||||
IfcStore.element_listeners.add(callback)
|
||||
|
||||
"""Keeps track of selected object names, typically during undo and redo
|
||||
|
||||
When any Blender object is stored outside a Blender PointerProperty, such as
|
||||
in a regular Python list, there is the likely probability that the object
|
||||
will be invalidated when undo or redo occurs. Object invalidation seems to
|
||||
only occur for selected objects either pre/post undo/redo event, including
|
||||
selected objects for consecutive undo/redos.
|
||||
|
||||
So if I first select o1, then o2, then o3, then press undo, o3 will be
|
||||
invalidated. If instead I press undo twice, o3 and o2 will be invalidated.
|
||||
"""
|
||||
@staticmethod
|
||||
def update_undo_redo_stack_objects():
|
||||
"""Keeps track of selected object names, typically during undo and redo
|
||||
|
||||
When any Blender object is stored outside a Blender PointerProperty, such as
|
||||
in a regular Python list, there is the likely probability that the object
|
||||
will be invalidated when undo or redo occurs. Object invalidation seems to
|
||||
only occur for selected objects either pre/post undo/redo event, including
|
||||
selected objects for consecutive undo/redos.
|
||||
|
||||
So if I first select o1, then o2, then o3, then press undo, o3 will be
|
||||
invalidated. If instead I press undo twice, o3 and o2 will be invalidated.
|
||||
"""
|
||||
if bpy.context.active_object:
|
||||
objects = set([o.name for o in bpy.context.selected_objects + [bpy.context.active_object]])
|
||||
else:
|
||||
@@ -183,22 +183,12 @@ class IfcStore:
|
||||
if is_top_level_operator:
|
||||
IfcStore.get_file().end_transaction()
|
||||
IfcStore.add_transaction_operation(
|
||||
operator, rollback=IfcStore.rollback_ifc_operator, commit=IfcStore.commit_ifc_operator
|
||||
operator, rollback=lambda d: IfcStore.get_file().undo(), commit=lambda d: IfcStore.get_file().redo()
|
||||
)
|
||||
IfcStore.end_transaction(operator)
|
||||
|
||||
return result
|
||||
|
||||
@staticmethod
|
||||
def rollback_ifc_operator(data):
|
||||
IfcStore.get_file().undo()
|
||||
blenderbim.bim.handler.purge_module_data()
|
||||
|
||||
@staticmethod
|
||||
def commit_ifc_operator(data):
|
||||
IfcStore.get_file().redo()
|
||||
blenderbim.bim.handler.purge_module_data()
|
||||
|
||||
@staticmethod
|
||||
def begin_transaction(operator):
|
||||
IfcStore.undo_redo_stack_objects = set()
|
||||
|
||||
@@ -64,10 +64,8 @@ class CreateProject(bpy.types.Operator):
|
||||
|
||||
def rollback(self, data):
|
||||
IfcStore.file = None
|
||||
blenderbim.bim.handler.purge_module_data()
|
||||
|
||||
def commit(self, data):
|
||||
blenderbim.bim.handler.purge_module_data()
|
||||
IfcStore.file = data["file"]
|
||||
|
||||
|
||||
@@ -106,10 +104,8 @@ class CreateProjectLibrary(bpy.types.Operator):
|
||||
|
||||
def rollback(self, data):
|
||||
IfcStore.file = None
|
||||
blenderbim.bim.handler.purge_module_data()
|
||||
|
||||
def commit(self, data):
|
||||
blenderbim.bim.handler.purge_module_data()
|
||||
IfcStore.file = data["file"]
|
||||
|
||||
|
||||
@@ -121,10 +117,12 @@ class SelectLibraryFile(bpy.types.Operator):
|
||||
filter_glob: bpy.props.StringProperty(default="*.ifc;*.ifczip;*.ifcxml", options={"HIDDEN"})
|
||||
|
||||
def execute(self, context):
|
||||
IfcStore.begin_transaction(self)
|
||||
old_filepath = IfcStore.library_path
|
||||
result = self._execute(context)
|
||||
self.transaction_data = {"old_filepath": old_filepath, "filepath": self.filepath}
|
||||
IfcStore.add_transaction_operation(self)
|
||||
IfcStore.end_transaction(self)
|
||||
return result
|
||||
|
||||
def _execute(self, context):
|
||||
@@ -229,10 +227,12 @@ class AssignLibraryDeclaration(bpy.types.Operator):
|
||||
definition: bpy.props.IntProperty()
|
||||
|
||||
def execute(self, context):
|
||||
IfcStore.begin_transaction(self)
|
||||
IfcStore.library_file.begin_transaction()
|
||||
result = self._execute(context)
|
||||
IfcStore.library_file.end_transaction()
|
||||
IfcStore.add_transaction_operation(self)
|
||||
IfcStore.end_transaction(self)
|
||||
return result
|
||||
|
||||
def _execute(self, context):
|
||||
@@ -263,10 +263,12 @@ class UnassignLibraryDeclaration(bpy.types.Operator):
|
||||
definition: bpy.props.IntProperty()
|
||||
|
||||
def execute(self, context):
|
||||
IfcStore.begin_transaction(self)
|
||||
IfcStore.library_file.begin_transaction()
|
||||
result = self._execute(context)
|
||||
IfcStore.library_file.end_transaction()
|
||||
IfcStore.add_transaction_operation(self)
|
||||
IfcStore.end_transaction(self)
|
||||
return result
|
||||
|
||||
def _execute(self, context):
|
||||
@@ -378,11 +380,13 @@ class EditHeader(bpy.types.Operator):
|
||||
bl_options = {"REGISTER", "UNDO"}
|
||||
|
||||
def execute(self, context):
|
||||
IfcStore.begin_transaction(self)
|
||||
self.transaction_data = {}
|
||||
self.transaction_data["old"] = self.record_state()
|
||||
result = self._execute(context)
|
||||
self.transaction_data["new"] = self.record_state()
|
||||
IfcStore.add_transaction_operation(self)
|
||||
IfcStore.end_transaction(self)
|
||||
return result
|
||||
|
||||
def _execute(self, context):
|
||||
|
||||
@@ -9,20 +9,46 @@ from blenderbim.bim.ifc import IfcStore
|
||||
class AddPsetTemplate(bpy.types.Operator):
|
||||
bl_idname = "bim.add_pset_template"
|
||||
bl_label = "Add Pset Template"
|
||||
bl_options = {"REGISTER", "UNDO"}
|
||||
|
||||
def execute(self, context):
|
||||
IfcStore.begin_transaction(self)
|
||||
IfcStore.pset_template_file.begin_transaction()
|
||||
result = self._execute(context)
|
||||
IfcStore.pset_template_file.end_transaction()
|
||||
IfcStore.add_transaction_operation(self)
|
||||
IfcStore.end_transaction(self)
|
||||
return result
|
||||
|
||||
def _execute(self, context):
|
||||
props = context.scene.BIMPsetTemplateProperties
|
||||
ifcopenshell.api.run("pset_template.add_pset_template", IfcStore.pset_template_file)
|
||||
Data.load(IfcStore.pset_template_file)
|
||||
updatePsetTemplates(self, context)
|
||||
return {"FINISHED"}
|
||||
|
||||
def rollback(self, data):
|
||||
IfcStore.pset_template_file.undo()
|
||||
|
||||
def commit(self, data):
|
||||
IfcStore.pset_template_file.redo()
|
||||
|
||||
|
||||
class RemovePsetTemplate(bpy.types.Operator):
|
||||
bl_idname = "bim.remove_pset_template"
|
||||
bl_label = "Remove Pset Template"
|
||||
bl_options = {"REGISTER", "UNDO"}
|
||||
|
||||
def execute(self, context):
|
||||
IfcStore.begin_transaction(self)
|
||||
IfcStore.pset_template_file.begin_transaction()
|
||||
result = self._execute(context)
|
||||
IfcStore.pset_template_file.end_transaction()
|
||||
IfcStore.add_transaction_operation(self)
|
||||
IfcStore.end_transaction(self)
|
||||
return result
|
||||
|
||||
def _execute(self, context):
|
||||
props = context.scene.BIMPsetTemplateProperties
|
||||
if props.active_pset_template_id == int(props.pset_templates):
|
||||
bpy.ops.bim.disable_editing_pset_template()
|
||||
@@ -33,10 +59,17 @@ class RemovePsetTemplate(bpy.types.Operator):
|
||||
updatePsetTemplates(self, context)
|
||||
return {"FINISHED"}
|
||||
|
||||
def rollback(self, data):
|
||||
IfcStore.pset_template_file.undo()
|
||||
|
||||
def commit(self, data):
|
||||
IfcStore.pset_template_file.redo()
|
||||
|
||||
|
||||
class EnableEditingPsetTemplate(bpy.types.Operator):
|
||||
bl_idname = "bim.enable_editing_pset_template"
|
||||
bl_label = "Enable Editing Pset Template"
|
||||
bl_options = {"REGISTER", "UNDO"}
|
||||
|
||||
def execute(self, context):
|
||||
props = context.scene.BIMPsetTemplateProperties
|
||||
@@ -53,6 +86,7 @@ class EnableEditingPsetTemplate(bpy.types.Operator):
|
||||
class DisableEditingPsetTemplate(bpy.types.Operator):
|
||||
bl_idname = "bim.disable_editing_pset_template"
|
||||
bl_label = "Disable Editing Pset Template"
|
||||
bl_options = {"REGISTER", "UNDO"}
|
||||
|
||||
def execute(self, context):
|
||||
props = context.scene.BIMPsetTemplateProperties
|
||||
@@ -63,6 +97,7 @@ class DisableEditingPsetTemplate(bpy.types.Operator):
|
||||
class EnableEditingPropTemplate(bpy.types.Operator):
|
||||
bl_idname = "bim.enable_editing_prop_template"
|
||||
bl_label = "Enable Editing Prop Template"
|
||||
bl_options = {"REGISTER", "UNDO"}
|
||||
prop_template: bpy.props.IntProperty()
|
||||
|
||||
def execute(self, context):
|
||||
@@ -78,6 +113,7 @@ class EnableEditingPropTemplate(bpy.types.Operator):
|
||||
class DisableEditingPropTemplate(bpy.types.Operator):
|
||||
bl_idname = "bim.disable_editing_prop_template"
|
||||
bl_label = "Disable Editing Prop Template"
|
||||
bl_options = {"REGISTER", "UNDO"}
|
||||
|
||||
def execute(self, context):
|
||||
props = context.scene.BIMPsetTemplateProperties
|
||||
@@ -88,8 +124,18 @@ class DisableEditingPropTemplate(bpy.types.Operator):
|
||||
class EditPsetTemplate(bpy.types.Operator):
|
||||
bl_idname = "bim.edit_pset_template"
|
||||
bl_label = "Edit Pset Template"
|
||||
bl_options = {"REGISTER", "UNDO"}
|
||||
|
||||
def execute(self, context):
|
||||
IfcStore.begin_transaction(self)
|
||||
IfcStore.pset_template_file.begin_transaction()
|
||||
result = self._execute(context)
|
||||
IfcStore.pset_template_file.end_transaction()
|
||||
IfcStore.add_transaction_operation(self)
|
||||
IfcStore.end_transaction(self)
|
||||
return result
|
||||
|
||||
def _execute(self, context):
|
||||
props = context.scene.BIMPsetTemplateProperties
|
||||
ifcopenshell.api.run("pset_template.edit_pset_template", IfcStore.pset_template_file, **{
|
||||
"pset_template": IfcStore.pset_template_file.by_id(props.active_pset_template_id),
|
||||
@@ -105,6 +151,13 @@ class EditPsetTemplate(bpy.types.Operator):
|
||||
bpy.ops.bim.disable_editing_pset_template()
|
||||
return {"FINISHED"}
|
||||
|
||||
def rollback(self, data):
|
||||
IfcStore.pset_template_file.undo()
|
||||
|
||||
def commit(self, data):
|
||||
IfcStore.pset_template_file.redo()
|
||||
|
||||
|
||||
|
||||
class SavePsetTemplateFile(bpy.types.Operator):
|
||||
bl_idname = "bim.save_pset_template_file"
|
||||
@@ -118,8 +171,18 @@ class SavePsetTemplateFile(bpy.types.Operator):
|
||||
class AddPropTemplate(bpy.types.Operator):
|
||||
bl_idname = "bim.add_prop_template"
|
||||
bl_label = "Add Prop Template"
|
||||
bl_options = {"REGISTER", "UNDO"}
|
||||
|
||||
def execute(self, context):
|
||||
IfcStore.begin_transaction(self)
|
||||
IfcStore.pset_template_file.begin_transaction()
|
||||
result = self._execute(context)
|
||||
IfcStore.pset_template_file.end_transaction()
|
||||
IfcStore.add_transaction_operation(self)
|
||||
IfcStore.end_transaction(self)
|
||||
return result
|
||||
|
||||
def _execute(self, context):
|
||||
props = context.scene.BIMPsetTemplateProperties
|
||||
pset_template_id = props.active_pset_template_id or int(props.pset_templates)
|
||||
ifcopenshell.api.run("pset_template.add_prop_template", IfcStore.pset_template_file, **{
|
||||
@@ -128,13 +191,29 @@ class AddPropTemplate(bpy.types.Operator):
|
||||
Data.load(IfcStore.pset_template_file)
|
||||
return {"FINISHED"}
|
||||
|
||||
def rollback(self, data):
|
||||
IfcStore.pset_template_file.undo()
|
||||
|
||||
def commit(self, data):
|
||||
IfcStore.pset_template_file.redo()
|
||||
|
||||
|
||||
class RemovePropTemplate(bpy.types.Operator):
|
||||
bl_idname = "bim.remove_prop_template"
|
||||
bl_label = "Remove Prop Template"
|
||||
bl_options = {"REGISTER", "UNDO"}
|
||||
prop_template: bpy.props.IntProperty()
|
||||
|
||||
def execute(self, context):
|
||||
IfcStore.begin_transaction(self)
|
||||
IfcStore.pset_template_file.begin_transaction()
|
||||
result = self._execute(context)
|
||||
IfcStore.pset_template_file.end_transaction()
|
||||
IfcStore.add_transaction_operation(self)
|
||||
IfcStore.end_transaction(self)
|
||||
return result
|
||||
|
||||
def _execute(self, context):
|
||||
props = context.scene.BIMPsetTemplateProperties
|
||||
ifcopenshell.api.run("pset_template.remove_prop_template", IfcStore.pset_template_file, **{
|
||||
"prop_template": IfcStore.pset_template_file.by_id(self.prop_template)
|
||||
@@ -142,12 +221,28 @@ class RemovePropTemplate(bpy.types.Operator):
|
||||
Data.load(IfcStore.pset_template_file)
|
||||
return {"FINISHED"}
|
||||
|
||||
def rollback(self, data):
|
||||
IfcStore.pset_template_file.undo()
|
||||
|
||||
def commit(self, data):
|
||||
IfcStore.pset_template_file.redo()
|
||||
|
||||
|
||||
class EditPropTemplate(bpy.types.Operator):
|
||||
bl_idname = "bim.edit_prop_template"
|
||||
bl_label = "Edit Prop Template"
|
||||
bl_options = {"REGISTER", "UNDO"}
|
||||
|
||||
def execute(self, context):
|
||||
IfcStore.begin_transaction(self)
|
||||
IfcStore.pset_template_file.begin_transaction()
|
||||
result = self._execute(context)
|
||||
IfcStore.pset_template_file.end_transaction()
|
||||
IfcStore.add_transaction_operation(self)
|
||||
IfcStore.end_transaction(self)
|
||||
return result
|
||||
|
||||
def _execute(self, context):
|
||||
props = context.scene.BIMPsetTemplateProperties
|
||||
ifcopenshell.api.run("pset_template.edit_prop_template", IfcStore.pset_template_file, **{
|
||||
"prop_template": IfcStore.pset_template_file.by_id(props.active_prop_template_id),
|
||||
@@ -160,3 +255,9 @@ class EditPropTemplate(bpy.types.Operator):
|
||||
Data.load(IfcStore.pset_template_file)
|
||||
bpy.ops.bim.disable_editing_prop_template()
|
||||
return {"FINISHED"}
|
||||
|
||||
def rollback(self, data):
|
||||
IfcStore.pset_template_file.undo()
|
||||
|
||||
def commit(self, data):
|
||||
IfcStore.pset_template_file.redo()
|
||||
|
||||
Reference in New Issue
Block a user