diff options
Diffstat (limited to 'release/scripts/startup/bl_operators/anim.py')
-rw-r--r-- | release/scripts/startup/bl_operators/anim.py | 107 |
1 files changed, 58 insertions, 49 deletions
diff --git a/release/scripts/startup/bl_operators/anim.py b/release/scripts/startup/bl_operators/anim.py index c20d591241c..0632f9bc3ca 100644 --- a/release/scripts/startup/bl_operators/anim.py +++ b/release/scripts/startup/bl_operators/anim.py @@ -28,15 +28,15 @@ if "bpy" in locals(): import bpy from bpy.types import Operator from bpy.props import ( - IntProperty, - BoolProperty, - EnumProperty, - StringProperty, - ) + IntProperty, + BoolProperty, + EnumProperty, + StringProperty, +) class ANIM_OT_keying_set_export(Operator): - "Export Keying Set to a python script" + """Export Keying Set to a python script""" bl_idname = "anim.keying_set_export" bl_label = "Export Keying Set..." @@ -102,43 +102,44 @@ class ANIM_OT_keying_set_export(Operator): if ksp.id in id_to_paths_cache: continue - """ - - idtype_list is used to get the list of id-datablocks from - bpy.data.* since this info isn't available elsewhere - - id.bl_rna.name gives a name suitable for UI, - with a capitalised first letter, but we need - the plural form that's all lower case - - special handling is needed for "nested" ID-blocks - (e.g. nodetree in Material) - """ + # - idtype_list is used to get the list of id-datablocks from + # bpy.data.* since this info isn't available elsewhere + # - id.bl_rna.name gives a name suitable for UI, + # with a capitalised first letter, but we need + # the plural form that's all lower case + # - special handling is needed for "nested" ID-blocks + # (e.g. nodetree in Material) if ksp.id.bl_rna.identifier.startswith("ShaderNodeTree"): # Find material or lamp using this node tree... id_bpy_path = "bpy.data.nodes[\"%s\"]" found = False - + for mat in bpy.data.materials: if mat.node_tree == ksp.id: id_bpy_path = "bpy.data.materials[\"%s\"].node_tree" % (mat.name) found = True - break; - + break + if not found: for lamp in bpy.data.lamps: if lamp.node_tree == ksp.id: id_bpy_path = "bpy.data.lamps[\"%s\"].node_tree" % (lamp.name) found = True - break; - + break + if not found: - self.report({'WARN'}, "Could not find material or lamp using Shader Node Tree - %s" % (ksp.id)) + self.report({'WARN'}, "Could not find material or lamp using Shader Node Tree - %s" % (ksp.id)) elif ksp.id.bl_rna.identifier.startswith("CompositorNodeTree"): # Find compositor nodetree using this node tree... for scene in bpy.data.scenes: if scene.node_tree == ksp.id: id_bpy_path = "bpy.data.scenes[\"%s\"].node_tree" % (scene.name) - break; + break else: - self.report({'WARN'}, "Could not find scene using Compositor Node Tree - %s" % (ksp.id)) + self.report({'WARN'}, "Could not find scene using Compositor Node Tree - %s" % (ksp.id)) + elif ksp.id.bl_rna.name == "Key": + # "keys" conflicts with a Python keyword, hence the simple solution won't work + id_bpy_path = "bpy.data.shape_keys[\"%s\"]" % (ksp.id.name) else: idtype_list = ksp.id.bl_rna.name.lower() + "s" id_bpy_path = "bpy.data.%s[\"%s\"]" % (idtype_list, ksp.id.name) @@ -197,7 +198,7 @@ class ANIM_OT_keying_set_export(Operator): class BakeAction(Operator): - """Bake object/pose loc/scale/rotation animation to a new action""" + """Bake all selected objects loc/scale/rotation animation to an action""" bl_idname = "nla.bake" bl_label = "Bake Action" bl_options = {'REGISTER', 'UNDO'} @@ -221,7 +222,7 @@ class BakeAction(Operator): default=1, ) only_selected = BoolProperty( - name="Only Selected", + name="Only Selected Bones", description="Only key selected bones (Pose baking only)", default=True, ) @@ -257,29 +258,27 @@ class BakeAction(Operator): ) def execute(self, context): - from bpy_extras import anim_utils + objects = context.selected_editable_objects + object_action_pairs = ( + [(obj, getattr(obj.animation_data, "action", None)) for obj in objects] + if self.use_current_action else + [(obj, None) for obj in objects] + ) - action = None - if self.use_current_action: - obj = context.object - if obj.animation_data: - action = obj.animation_data.action - - action = anim_utils.bake_action(self.frame_start, - self.frame_end, - frame_step=self.step, - only_selected=self.only_selected, - do_pose='POSE' in self.bake_types, - do_object='OBJECT' in self.bake_types, - do_visual_keying=self.visual_keying, - do_constraint_clear=self.clear_constraints, - do_parents_clear=self.clear_parents, - do_clean=True, - action=action, - ) - - if action is None: + actions = anim_utils.bake_action_objects( + object_action_pairs, + frames=range(self.frame_start, self.frame_end + 1, self.step), + only_selected=self.only_selected, + do_pose='POSE' in self.bake_types, + do_object='OBJECT' in self.bake_types, + do_visual_keying=self.visual_keying, + do_constraint_clear=self.clear_constraints, + do_parents_clear=self.clear_parents, + do_clean=True, + ) + + if not any(actions): self.report({'INFO'}, "Nothing to bake") return {'CANCELLED'} @@ -302,9 +301,11 @@ class ClearUselessActions(Operator): bl_label = "Clear Useless Actions" bl_options = {'REGISTER', 'UNDO'} - only_unused = BoolProperty(name="Only Unused", + only_unused = BoolProperty( + name="Only Unused", description="Only unused (Fake User only) actions get considered", - default=True) + default=True, + ) @classmethod def poll(cls, context): @@ -393,7 +394,7 @@ class UpdateAnimatedTransformConstraint(Operator): except: pass ret = (data, new_path) - #print(ret) + # print(ret) return ret @@ -412,3 +413,11 @@ class UpdateAnimatedTransformConstraint(Operator): text.from_string(log) self.report({'INFO'}, "Complete report available on '%s' text datablock" % text.name) return {'FINISHED'} + + +classes = ( + ANIM_OT_keying_set_export, + BakeAction, + ClearUselessActions, + UpdateAnimatedTransformConstraint, +) |