Housekeeping (bug fixes)

NEW FEATURES:
- added apply shapekey to basis from Cats
  - now that pesky thing I keep going back to cats for is in Avatar Toolkit.

BUG FIXES:
- now we push armature santizers into functions where they are needed
  - this prevents the methods from mirroring changes while working, causing them to blow up when mirror mode is on
  - more changes to come for armature setting santitizers
- fixed error reporting
  - now methods when catching errors will return full error tracebacks
  - this will help make debugging and finding user issues easier.
This commit is contained in:
989onan
2025-07-10 18:44:42 -04:00
parent 89fc8bc9c8
commit 6d9f751a16
27 changed files with 663 additions and 143 deletions
View File
@@ -13,6 +13,8 @@ from ...core.common import (
join_mesh_objects,
remove_unused_shapekeys,
identify_bones,
store_breaking_settings_armature,
restore_breaking_settings_armature,
)
from ...core.dictionaries import simplify_bonename
@@ -42,6 +44,9 @@ class AvatarToolkit_OT_MergeArmature(bpy.types.Operator):
logger.error(f"Armature not found: {merge_armature_name}")
self.report({'ERROR'}, t('MergeArmature.error.not_found', name=merge_armature_name))
return {'CANCELLED'}
#Store current armature settings that can mess us up.
data_breaking_base = store_breaking_settings_armature(base_armature)
data_breaking_merge = store_breaking_settings_armature(merge_armature)
# Remove Rigid Bodies and Joints
delete_rigidbodies_and_joints(base_armature)
@@ -70,7 +75,11 @@ class AvatarToolkit_OT_MergeArmature(bpy.types.Operator):
wm.progress_update(100)
wm.progress_end()
restore_breaking_settings_armature(base_armature, data_breaking_base)
restore_breaking_settings_armature(merge_armature, data_breaking_merge)
self.report({'INFO'}, t('MergeArmature.success'))
return {'FINISHED'}
except Exception as e:
@@ -117,14 +117,11 @@ class AvatarToolkit_OT_ApplyModifierForShapkeyObj(bpy.types.Operator):
obj.select_set(True)
context.view_layer.objects.active = obj
bpy.ops.object.join_shapes()
except Exception as e:
except Exception:
self.report({'ERROR'}, f"Shapekey joining failed!!")
print(f"Shapekey joining failed!!")
print(traceback.format_exc(e))
#clean up after critical failure
for shape in shapes:
bpy.data.objects.remove(shape)#faster than ops delete
print(traceback.format_exc())
#final clean up
for shape in shapes:
@@ -136,4 +133,6 @@ class AvatarToolkit_OT_ApplyModifierForShapkeyObj(bpy.types.Operator):
return {'FINISHED'}
return {'FINISHED'}
+10 -6
View File
@@ -2,6 +2,7 @@ import bpy
from bpy.types import Operator, Context, Object, ArmatureModifier, VertexGroup
from mathutils import Vector
from typing import Set, Optional, List, Any
import traceback
from ...core.logging_setup import logger
from ...core.translations import t
@@ -10,7 +11,9 @@ from ...core.common import (
get_all_meshes,
ProgressTracker,
calculate_bone_orientation,
add_armature_modifier
add_armature_modifier,
store_breaking_settings_armature,
restore_breaking_settings_armature,
)
from ...core.armature_validation import validate_armature
@@ -83,11 +86,11 @@ class AvatarToolkit_OT_AttachMesh(Operator):
attach_to_bone = armature.data.edit_bones.get(attach_bone_name)
if not attach_to_bone:
raise ValueError(t("AttachMesh.error.bone_not_found", bone=attach_bone_name))
data_breaking = store_breaking_settings_armature(armature)
mesh_bone = armature.data.edit_bones.new(mesh_name)
mesh_bone.parent = attach_to_bone
progress.step(t("AttachMesh.create_bone"))
# Calculate bone placement
verts_in_group: List[Any] = [v for v in mesh.data.vertices
for g in v.groups if g.group == vg.index]
@@ -104,6 +107,7 @@ class AvatarToolkit_OT_AttachMesh(Operator):
mesh_bone.head = center
mesh_bone.tail = center + Vector((0, 0, max(0.1, dimensions.z)))
mesh_bone.roll = roll_angle
restore_breaking_settings_armature(armature, data_breaking)
progress.step(t("AttachMesh.position_bone"))
bpy.ops.object.mode_set(mode='OBJECT')
@@ -114,9 +118,9 @@ class AvatarToolkit_OT_AttachMesh(Operator):
self.report({'INFO'}, t("AttachMesh.success"))
return {'FINISHED'}
except Exception as e:
logger.error(f"Failed to attach mesh: {str(e)}")
self.report({'ERROR'}, str(e))
except Exception:
logger.error(f"Failed to attach mesh: {traceback.format_exc()}")
self.report({'ERROR'}, traceback.format_exc())
return {'CANCELLED'}
def validate_mesh_transforms(mesh: Optional[Object]) -> tuple[bool, str]: