From 8441bf92a85bda146fca2abaaa34ecf5dc1b375d Mon Sep 17 00:00:00 2001 From: mike zyracki Date: Wed, 17 Jul 2019 01:10:05 -0400 Subject: [PATCH] Add bWasCreated flag to BindToSkeletalMesh so when we know when we create the sequencer anim instance we should save the pose. This removes the need for control rig to override NativeInitialization. Also add some checks to make sure we save a valid pose. #jira UE-76569 #rb max.chen #ROBOMERGE-OWNER: ben.marsh #ROBOMERGE-AUTHOR: mike.zyracki #ROBOMERGE-SOURCE: CL 7280102 in //UE4/Release-4.23/... via CL 7280144 #ROBOMERGE-BOT: BUILD (Main -> Dev-Build) (v371-7306989) [CL 7350675 by mike zyracki in Dev-Build branch] --- .../Private/Sequencer/ControlRigBindingTemplate.cpp | 3 ++- .../Sequencer/ControlRigSequencerAnimInstance.cpp | 6 ------ .../Sequencer/ControlRigSequencerAnimInstance.h | 1 - .../Private/Editor/ControlRigEditor.cpp | 6 ++++-- .../Persona/Private/AnimationEditorPreviewScene.cpp | 3 ++- .../Private/AnimSequencerInstance.cpp | 13 +++++++------ .../AnimGraphRuntime/Public/AnimCustomInstance.h | 4 +++- .../AnimGraphRuntime/Public/AnimSequencerInstance.h | 7 ++++--- .../MovieSceneSkeletalAnimationTemplate.cpp | 8 ++++++-- 9 files changed, 28 insertions(+), 23 deletions(-) diff --git a/Engine/Plugins/Experimental/ControlRig/Source/ControlRig/Private/Sequencer/ControlRigBindingTemplate.cpp b/Engine/Plugins/Experimental/ControlRig/Source/ControlRig/Private/Sequencer/ControlRigBindingTemplate.cpp index 567ca3899cd5..bf7d533c3b88 100644 --- a/Engine/Plugins/Experimental/ControlRig/Source/ControlRig/Private/Sequencer/ControlRigBindingTemplate.cpp +++ b/Engine/Plugins/Experimental/ControlRig/Source/ControlRig/Private/Sequencer/ControlRigBindingTemplate.cpp @@ -83,7 +83,8 @@ struct FBindControlRigObjectToken : IMovieSceneExecutionToken check(ControlRig); if (USkeletalMeshComponent* SkeletalMeshComponent = Cast(ControlRig->GetObjectBinding()->GetBoundObject())) { - if (UControlRigSequencerAnimInstance* AnimInstance = UAnimCustomInstance::BindToSkeletalMeshComponent(SkeletalMeshComponent)) + bool bWasCreated = false; + if (UControlRigSequencerAnimInstance* AnimInstance = UAnimCustomInstance::BindToSkeletalMeshComponent(SkeletalMeshComponent,bWasCreated)) { AnimInstance->RecalcRequiredBones(); } diff --git a/Engine/Plugins/Experimental/ControlRig/Source/ControlRig/Private/Sequencer/ControlRigSequencerAnimInstance.cpp b/Engine/Plugins/Experimental/ControlRig/Source/ControlRig/Private/Sequencer/ControlRigSequencerAnimInstance.cpp index 822ac4c34762..43d20711599e 100644 --- a/Engine/Plugins/Experimental/ControlRig/Source/ControlRig/Private/Sequencer/ControlRigSequencerAnimInstance.cpp +++ b/Engine/Plugins/Experimental/ControlRig/Source/ControlRig/Private/Sequencer/ControlRigSequencerAnimInstance.cpp @@ -20,9 +20,3 @@ bool UControlRigSequencerAnimInstance::UpdateControlRig(UControlRig* InControlRi CachedControlRig = InControlRig; return GetProxyOnGameThread().UpdateControlRig(InControlRig, SequenceId, bAdditive, bApplyBoneFilter, BoneFilter, Weight, bExternalSource); } - -void UControlRigSequencerAnimInstance::NativeInitializeAnimation() -{ - //Do nothing since UAnimSequencerInstance save's a pose snapshot which can cause ensure and crash issues - //since it may not have a skeletal mesh or component transform set up yet. -} diff --git a/Engine/Plugins/Experimental/ControlRig/Source/ControlRig/Public/Sequencer/ControlRigSequencerAnimInstance.h b/Engine/Plugins/Experimental/ControlRig/Source/ControlRig/Public/Sequencer/ControlRigSequencerAnimInstance.h index f46d10fe8953..65d73606cc70 100644 --- a/Engine/Plugins/Experimental/ControlRig/Source/ControlRig/Public/Sequencer/ControlRigSequencerAnimInstance.h +++ b/Engine/Plugins/Experimental/ControlRig/Source/ControlRig/Public/Sequencer/ControlRigSequencerAnimInstance.h @@ -22,5 +22,4 @@ public: protected: // UAnimInstance interface virtual FAnimInstanceProxy* CreateAnimInstanceProxy() override; - virtual void NativeInitializeAnimation() override; }; diff --git a/Engine/Plugins/Experimental/ControlRig/Source/ControlRigEditor/Private/Editor/ControlRigEditor.cpp b/Engine/Plugins/Experimental/ControlRig/Source/ControlRigEditor/Private/Editor/ControlRigEditor.cpp index 4587d2879c34..2800b462e57c 100644 --- a/Engine/Plugins/Experimental/ControlRig/Source/ControlRigEditor/Private/Editor/ControlRigEditor.cpp +++ b/Engine/Plugins/Experimental/ControlRig/Source/ControlRigEditor/Private/Editor/ControlRigEditor.cpp @@ -1238,7 +1238,8 @@ void FControlRigEditor::HandlePreviewSceneCreated(const TSharedRef(Actor); EditorSkelComp->SetSkeletalMesh(InPersonaPreviewScene->GetPersonaToolkit()->GetPreviewMesh()); InPersonaPreviewScene->SetPreviewMeshComponent(EditorSkelComp); - UAnimCustomInstance::BindToSkeletalMeshComponent(EditorSkelComp); + bool bWasCreated = false; + UAnimCustomInstance::BindToSkeletalMeshComponent(EditorSkelComp, bWasCreated); InPersonaPreviewScene->AddComponent(EditorSkelComp, FTransform::Identity); // set root component, so we can attach to it. @@ -1328,7 +1329,8 @@ void FControlRigEditor::RebindToSkeletalMeshComponent() UDebugSkelMeshComponent* MeshComponent = GetPersonaToolkit()->GetPreviewScene()->GetPreviewMeshComponent(); if (MeshComponent) { - UAnimCustomInstance::BindToSkeletalMeshComponent(MeshComponent); + bool bWasCreated = false; + UAnimCustomInstance::BindToSkeletalMeshComponent(MeshComponent , bWasCreated); } } diff --git a/Engine/Source/Editor/Persona/Private/AnimationEditorPreviewScene.cpp b/Engine/Source/Editor/Persona/Private/AnimationEditorPreviewScene.cpp index e846131b5150..c96221879eb0 100644 --- a/Engine/Source/Editor/Persona/Private/AnimationEditorPreviewScene.cpp +++ b/Engine/Source/Editor/Persona/Private/AnimationEditorPreviewScene.cpp @@ -352,7 +352,8 @@ void FAnimationEditorPreviewScene::RefreshAdditionalMeshes(bool bAllowOverrideBa } else { - UAnimCustomInstance::BindToSkeletalMeshComponent(NewComp); + bool bWasCreated = false; + UAnimCustomInstance::BindToSkeletalMeshComponent(NewComp,bWasCreated); } AdditionalMeshes.Add(NewComp); diff --git a/Engine/Source/Runtime/AnimGraphRuntime/Private/AnimSequencerInstance.cpp b/Engine/Source/Runtime/AnimGraphRuntime/Private/AnimSequencerInstance.cpp index 9cc09df1677a..eeaaef18e5b7 100644 --- a/Engine/Source/Runtime/AnimGraphRuntime/Private/AnimSequencerInstance.cpp +++ b/Engine/Source/Runtime/AnimGraphRuntime/Private/AnimSequencerInstance.cpp @@ -40,12 +40,13 @@ void UAnimSequencerInstance::ResetPose() GetProxyOnGameThread().ResetPose(); } -void UAnimSequencerInstance::NativeInitializeAnimation() -{ - SavePose(); -} - void UAnimSequencerInstance::SavePose() { - SavePoseSnapshot(UAnimSequencerInstance::SequencerPoseName); + if (USkeletalMeshComponent* SkeletalMeshComponent = GetSkelMeshComponent()) + { + if (SkeletalMeshComponent->SkeletalMesh && SkeletalMeshComponent->GetComponentSpaceTransforms().Num() > 0) + { + SavePoseSnapshot(UAnimSequencerInstance::SequencerPoseName); + } + } } diff --git a/Engine/Source/Runtime/AnimGraphRuntime/Public/AnimCustomInstance.h b/Engine/Source/Runtime/AnimGraphRuntime/Public/AnimCustomInstance.h index a00464d82f7e..61bfd7106ab6 100644 --- a/Engine/Source/Runtime/AnimGraphRuntime/Public/AnimCustomInstance.h +++ b/Engine/Source/Runtime/AnimGraphRuntime/Public/AnimCustomInstance.h @@ -21,8 +21,9 @@ class ANIMGRAPHRUNTIME_API UAnimCustomInstance : public UAnimInstance * @return the current (or newly created) UAnimCustomInstance */ template - static InstanceClassType* BindToSkeletalMeshComponent(USkeletalMeshComponent* InSkeletalMeshComponent) + static InstanceClassType* BindToSkeletalMeshComponent(USkeletalMeshComponent* InSkeletalMeshComponent, bool& bOutWasCreated) { + bOutWasCreated = false; // make sure to tick and refresh all the time when ticks // @TODO: this needs restoring post-binding InSkeletalMeshComponent->VisibilityBasedAnimTickOption = EVisibilityBasedAnimTickOption::AlwaysTickPoseAndRefreshBones; @@ -50,6 +51,7 @@ class ANIMGRAPHRUNTIME_API UAnimCustomInstance : public UAnimInstance InstanceClassType* SequencerInstance = NewObject(InSkeletalMeshComponent, InstanceClassType::StaticClass()); InSkeletalMeshComponent->AnimScriptInstance = SequencerInstance; InSkeletalMeshComponent->AnimScriptInstance->InitializeAnimation(); + bOutWasCreated = true; return SequencerInstance; } else diff --git a/Engine/Source/Runtime/AnimGraphRuntime/Public/AnimSequencerInstance.h b/Engine/Source/Runtime/AnimGraphRuntime/Public/AnimSequencerInstance.h index b0dc57018668..5db2dd8dd2d7 100644 --- a/Engine/Source/Runtime/AnimGraphRuntime/Public/AnimSequencerInstance.h +++ b/Engine/Source/Runtime/AnimGraphRuntime/Public/AnimSequencerInstance.h @@ -27,13 +27,14 @@ public: /** Reset the pose for this instance*/ void ResetPose(); + /** Saved the named pose to restore after */ + void SavePose(); + protected: // UAnimInstance interface virtual FAnimInstanceProxy* CreateAnimInstanceProxy() override; - virtual void NativeInitializeAnimation() override; - /** Saved the named pose to restore after */ - void SavePose(); + public: static const FName SequencerPoseName; diff --git a/Engine/Source/Runtime/MovieSceneTracks/Private/Evaluation/MovieSceneSkeletalAnimationTemplate.cpp b/Engine/Source/Runtime/MovieSceneTracks/Private/Evaluation/MovieSceneSkeletalAnimationTemplate.cpp index c802fbe884c1..35bcf8d81668 100644 --- a/Engine/Source/Runtime/MovieSceneTracks/Private/Evaluation/MovieSceneSkeletalAnimationTemplate.cpp +++ b/Engine/Source/Runtime/MovieSceneTracks/Private/Evaluation/MovieSceneSkeletalAnimationTemplate.cpp @@ -236,8 +236,12 @@ namespace MovieScene OriginalStack.SavePreAnimatedState(Player, *SkeletalMeshComponent, GetAnimControlTypeID(), FPreAnimatedAnimationTokenProducer()); UAnimInstance* ExistingAnimInstance = SkeletalMeshComponent->GetAnimInstance(); - - UAnimSequencerInstance* SequencerInstance = UAnimCustomInstance::BindToSkeletalMeshComponent(SkeletalMeshComponent); + bool bWasCreated = false; + UAnimSequencerInstance* SequencerInstance = UAnimCustomInstance::BindToSkeletalMeshComponent(SkeletalMeshComponent,bWasCreated); + if (bWasCreated) + { + SequencerInstance->SavePose(); + } const bool bPreviewPlayback = ShouldUsePreviewPlayback(Player, *SkeletalMeshComponent);