public static AnimationCurve[] GenerateBlendshapeCurves(FaceData parsedData) { float fps = parsedData.fps != 0f ? parsedData.fps : DefaultFPS; var blendshapeNames = parsedData.blendShapesNames; var curves = new AnimationCurve[blendshapeNames.Length]; var frames = parsedData.frames; for (int i = 0; i < curves.Length; i++) { var animationCurve = new AnimationCurve(); for (int j = 0; j < frames.Length; j++) { var frame = frames[j]; float time = j / fps; float value = frame.blendshapes[i]; // TODO: add support for custom curve interpolation var keyframe = new Keyframe(time, value); animationCurve.AddKey(keyframe); } curves[i] = animationCurve; } return(curves); }
public static PoseCurve[] GenerateBonesCurves(FaceData parsedData, Animator targetAnim) { float fps = parsedData.fps != 0f ? parsedData.fps : DefaultFPS; var bonesNames = parsedData.bonesNames; var curves = new List <PoseCurve>(); var frames = parsedData.frames; for (int i = 0; i < bonesNames.Length; i++) { var poseCurve = new PoseCurve(); var rotCurves = new List <AnimationCurve>(); var boneName = bonesNames[i]; var targetBone = FindBone(targetAnim.transform, boneName); if (targetBone == null) { Debug.LogWarning($"Can't find {boneName} bone. " + $"Add NamedBoneComponet to {boneName} GameObject"); continue; } // record each roation as 4 curves // in quaternion xyzw order for (int ax = 0; ax < 4; ax++) { var animationCurve = new AnimationCurve(); for (int j = 0; j < frames.Length; j++) { var frame = frames[j]; var rot = frame.bones[i].Transform.rotation; var fRot = targetBone.ApplyBoneTransformation(rot); float time = j / fps; var value = fRot[ax]; // TODO: add support for custom curve interpolation var keyframe = new Keyframe(time, value); animationCurve.AddKey(keyframe); } rotCurves.Add(animationCurve); } poseCurve.rotation = rotCurves.ToArray(); curves.Add(poseCurve); } return(curves.ToArray()); }
public void SetAnimationToPlay(FaceData currentData, UniversalPlayer linkedPlayer = null, float timeToSwitch = 0f, bool loop = false) { IsPlaying = true; this.player = linkedPlayer; this.currentData = currentData; this.isLoop = loop; if (jsonToUnityBlendMap == null) { PrepareBlendshapesMapping(); } if (jsonToUnityBoneMap == null) { PrepareBonesMapping(); } StopAllCoroutines(); StartCoroutine(PlayingRoutine(timeToSwitch)); }