glTF exporter: fix objects parented to bone animated when using rest pose as default
This commit is contained in:
parent
58db76bcc6
commit
4cb6ebd874
|
@ -4,7 +4,7 @@
|
|||
bl_info = {
|
||||
'name': 'glTF 2.0 format',
|
||||
'author': 'Julien Duroure, Scurest, Norbert Nopper, Urs Hanselmann, Moritz Becher, Benjamin Schmithüsen, Jim Eckerlein, and many external contributors',
|
||||
"version": (3, 4, 16),
|
||||
"version": (3, 4, 17),
|
||||
'blender': (3, 3, 0),
|
||||
'location': 'File > Import-Export',
|
||||
'description': 'Import-Export as glTF 2.0',
|
||||
|
|
|
@ -19,6 +19,35 @@ from io_scene_gltf2.blender.exp.gltf2_blender_gather_tree import VExportNode
|
|||
from . import gltf2_blender_export_keys
|
||||
|
||||
|
||||
def gather_channels_baked(obj_uuid, export_settings):
|
||||
channels = []
|
||||
|
||||
# If no animation in file, no need to bake
|
||||
if len(bpy.data.actions) == 0:
|
||||
return None
|
||||
|
||||
start_frame = min([v[0] for v in [a.frame_range for a in bpy.data.actions]])
|
||||
end_frame = max([v[1] for v in [a.frame_range for a in bpy.data.actions]])
|
||||
|
||||
for p in ["location", "rotation_quaternion", "scale"]:
|
||||
channel = gather_animation_channel(
|
||||
obj_uuid,
|
||||
(),
|
||||
export_settings,
|
||||
None,
|
||||
p,
|
||||
start_frame,
|
||||
end_frame,
|
||||
False,
|
||||
obj_uuid, # Use obj uuid as action name for caching
|
||||
None,
|
||||
False #If Object is not animated, don't keep animation for this channel
|
||||
)
|
||||
if channel is not None:
|
||||
channels.append(channel)
|
||||
|
||||
return channels if len(channels) > 0 else None
|
||||
|
||||
@cached
|
||||
def gather_animation_channels(obj_uuid: int,
|
||||
blender_action: bpy.types.Action,
|
||||
|
@ -118,6 +147,21 @@ def gather_animation_channels(obj_uuid: int,
|
|||
if channel is not None:
|
||||
channels.append(channel)
|
||||
|
||||
# When An Object is parented to bone, and rest pose is used (not current frame)
|
||||
# If parenting is not done with same TRS than rest pose, this can lead to inconsistencies
|
||||
# So we need to bake object animation too, to be sure that correct TRS animation are used
|
||||
# Here, we want add these channels to same action that the armature
|
||||
if export_settings['gltf_selected'] is False and export_settings['gltf_current_frame'] is False:
|
||||
|
||||
children_obj_parent_to_bones = []
|
||||
for bone_uuid in bones_uuid:
|
||||
children_obj_parent_to_bones.extend([child for child in export_settings['vtree'].nodes[bone_uuid].children if export_settings['vtree'].nodes[child].blender_type != VExportNode.BONE])
|
||||
for child_uuid in children_obj_parent_to_bones:
|
||||
|
||||
channels_baked = gather_channels_baked(child_uuid, export_settings)
|
||||
if channels_baked is not None:
|
||||
channels.extend(channels_baked)
|
||||
|
||||
else:
|
||||
done_paths = []
|
||||
for channel_group in __get_channel_groups(blender_action, blender_object, export_settings):
|
||||
|
|
|
@ -13,35 +13,6 @@ from io_scene_gltf2.blender.exp.gltf2_blender_gather_tree import VExportNode
|
|||
from ..com.gltf2_blender_data_path import is_bone_anim_channel
|
||||
|
||||
|
||||
def __gather_channels_baked(obj_uuid, export_settings):
|
||||
channels = []
|
||||
|
||||
# If no animation in file, no need to bake
|
||||
if len(bpy.data.actions) == 0:
|
||||
return None
|
||||
|
||||
start_frame = min([v[0] for v in [a.frame_range for a in bpy.data.actions]])
|
||||
end_frame = max([v[1] for v in [a.frame_range for a in bpy.data.actions]])
|
||||
|
||||
for p in ["location", "rotation_quaternion", "scale"]:
|
||||
channel = gltf2_blender_gather_animation_channels.gather_animation_channel(
|
||||
obj_uuid,
|
||||
(),
|
||||
export_settings,
|
||||
None,
|
||||
p,
|
||||
start_frame,
|
||||
end_frame,
|
||||
False,
|
||||
obj_uuid, # Use obj uuid as action name for caching
|
||||
None,
|
||||
False #If Object is not animated, don't keep animation for this channel
|
||||
)
|
||||
if channel is not None:
|
||||
channels.append(channel)
|
||||
|
||||
return channels if len(channels) > 0 else None
|
||||
|
||||
def gather_animations( obj_uuid: int,
|
||||
tracks: typing.Dict[str, typing.List[int]],
|
||||
offset: int,
|
||||
|
@ -69,7 +40,7 @@ def gather_animations( obj_uuid: int,
|
|||
# We also have to check if this is a skinned mesh, because we don't have to force animation baking on this case
|
||||
# (skinned meshes TRS must be ignored, says glTF specification)
|
||||
if export_settings['vtree'].nodes[obj_uuid].skin is None:
|
||||
channels = __gather_channels_baked(obj_uuid, export_settings)
|
||||
channels = gltf2_blender_gather_animation_channels.gather_channels_baked(obj_uuid, export_settings)
|
||||
if channels is not None:
|
||||
animation = gltf2_io.Animation(
|
||||
channels=channels,
|
||||
|
|
Loading…
Reference in New Issue