public IEnumerable <TaskInfo> SmoothIE(int iterations, float smoothMin, float smoothMax, float easeOffset, float easeLength) { FramesArray smoothed = new FramesArray(this); FramesArray temp = new FramesArray(this); for (int i = 0; i < iterations; i++) { for (int v = 0; v < smoothed.VerticesCount; v++) { for (int f = 0; f < smoothed.Count; f++) { smoothed[f, v] = BPoint(temp[f - 1, v], temp[f, v], temp[f + 1, v], temp[f + 2, v]); } } temp = new FramesArray(smoothed); yield return(new TaskInfo("Smoothing", i / (float)iterations)); } for (int v = 0; v < smoothed.VerticesCount; v++) { for (int f = 0; f < Count; f++) { float pers = (float)f / (float)(Count - 1); float lv = Extension.SmoothLoopCurve(pers, smoothMin, smoothMax, easeOffset, easeLength); this[f, v] = Vector3.LerpUnclamped(this[f, v], smoothed[f, v], lv); } } yield return(new TaskInfo("Smoothing", 1f)); }
public FramesArray(FramesArray source) { frames = new List <Vector3[]>(source.frames); IsLoop = source.IsLoop; Interpolation = source.Interpolation; }
public IEnumerable <TaskInfo> Build() { Frames = new FramesArray(cis.IsLoop, cis.SubFrameInterpolation); FramesArray TransitionFrames = new FramesArray(false, InterpolateModeEnum.Linear); int readFramesCounter = 0; if (IsMeshSequence) { MeshSequenceInfo msi = new MeshSequenceInfo(cis.FilePath, MeshSequenceInfo.SortModeEnum.ByNumber); for (int f = cis.EndTransitionFrom; f < cis.EndTransitionTo; f++) { Vector3[] objVertices = ObjData.GetVerticesFromObj(msi.infos[f].fi.FullName, cis.SwapYZAxis, cis.Scale); TransitionFrames.AddFrame(objVertices); readFramesCounter++; yield return(tstack["Read .obj sequence"].GetInfo(readFramesCounter)); } for (int f = cis.ImportRangeFrom; f < cis.ImportRangeTo; f++) { Vector3[] objVertices = ObjData.GetVerticesFromObj(msi.infos[f].fi.FullName, cis.SwapYZAxis, cis.Scale); if (objVertices.Length != geometryVerticesCount) { yield return(new TaskInfo(string.Format("Error: frame {0} vertex count mismatch", msi.infos[f].fi.FullName), -1)); } Frames.AddFrame(objVertices); readFramesCounter++; yield return(tstack["Read .obj sequence"].GetInfo(readFramesCounter)); } for (int f = cis.BeginTransitionFrom; f < cis.BeginTransitionTo; f++) { Vector3[] objVertices = ObjData.GetVerticesFromObj(msi.infos[f].fi.FullName, cis.SwapYZAxis, cis.Scale); TransitionFrames.AddFrame(objVertices); readFramesCounter++; yield return(tstack["Read .obj sequence"].GetInfo(readFramesCounter)); } } else { Name = (new FileInfo(cis.FilePath)).Name; FileStream fs = new FileStream(cis.FilePath, FileMode.Open); BinaryReader binReader = new BinaryReader(fs); binReader.ReadChars(12); //signature binReader.ReadInt32(); //file version int VerticesCount = binReader.ReadInt32(); binReader.ReadSingle(); // start frame binReader.ReadSingle(); //sample rate binReader.ReadInt32(); // int sourceFramesCount; for (int f = 0; f < cis.EndTransitionFrom; f++) { for (int v = 0; v < VerticesCount; v++) { binReader.ReadSingle(); binReader.ReadSingle(); binReader.ReadSingle(); } } // end transition for (int f = cis.EndTransitionFrom; f < cis.EndTransitionTo; f++) { TransitionFrames.AddFrame(ReadFrame(binReader, geometryVerticesCount)); readFramesCounter++; yield return(tstack["Read .pc2 file"].GetInfo(readFramesCounter)); } // frames for (int f = cis.ImportRangeFrom; f < cis.ImportRangeTo; f++) { Frames.AddFrame(ReadFrame(binReader, geometryVerticesCount)); readFramesCounter++; yield return(tstack["Read .pc2 file"].GetInfo(readFramesCounter)); } // begin transition for (int f = cis.BeginTransitionFrom; f < cis.BeginTransitionTo; f++) { TransitionFrames.AddFrame(ReadFrame(binReader, geometryVerticesCount)); readFramesCounter++; yield return(tstack["Read .pc2 file"].GetInfo(readFramesCounter)); } #if UNITY_WSA binReader.Dispose(); fs.Dispose(); #else binReader.Close(); fs.Close(); #endif } if (cis.TransitionMode == TransitionModeEnum.Begin) { for (int f = 0; f < TransitionFrames.Count; f++) { float flv = f / (float)TransitionFrames.Count; flv = Extension.LinearToSin(flv); for (int v = 0; v < geometryVerticesCount; v++) { Vector3 sVert = Vector3.LerpUnclamped(TransitionFrames[f, v], Frames[f, v], flv); Frames[f, v] = sVert; } } } if (cis.TransitionMode == TransitionModeEnum.End) { for (int f = 0; f < TransitionFrames.Count; f++) { float flv = f / (float)TransitionFrames.Count; flv = Extension.LinearToSin(flv); int frameIdx = Frames.Count - f - 1; int transitionIdx = TransitionFrames.Count - f - 1; for (int v = 0; v < geometryVerticesCount; v++) { Vector3 sVert = Vector3.LerpUnclamped(TransitionFrames[transitionIdx, v], Frames[frameIdx, v], flv); Frames[frameIdx, v] = sVert; } } } if (cis.ChangeFramesCount) { FramesArray retimedFrames = new FramesArray(cis.ClampedCustomFramesCount, Frames.VerticesCount, cis.IsLoop, cis.SubFrameInterpolation); float step = cis.IsLoop ? 1f / (float)cis.CustomFramesCount : 1f / (cis.ClampedCustomFramesCount - 1); for (int f = 0; f < retimedFrames.Count; f++) { float persentage = f * step; for (int v = 0; v < Frames.VerticesCount; v++) { retimedFrames[f, v] = Frames[persentage, v]; } yield return(tstack["Change frames count"].GetInfo(f)); } Frames = retimedFrames; } if (cis.EnableMotionSmoothing) { foreach (TaskInfo ti in Frames.SmoothIE(cis.MotionSmoothIterations, cis.MotionSmoothAmountMin, cis.MotionSmoothAmountMax, cis.MotionSmoothEaseOffset, cis.MotionSmoothEaseLength)) { yield return(tstack["Motion smoothing"].GetInfo(ti.Persentage)); } } if (cis.EnableNormalizeSpeed) { for (int v = 0; v < Frames.VerticesCount; v++) { Vector3[] modified = Frames[v]; if (cis.IsLoop) { Vector3[] modifiedLooped = new Vector3[modified.Length + 1]; modified.CopyTo(modifiedLooped, 0); modifiedLooped[modifiedLooped.Length - 1] = modifiedLooped[0]; modified = modifiedLooped; } NormalizedSpline ns = new NormalizedSpline(modified); float stepMult = 1f / (modified.Length - 1); for (int f = 0; f < modified.Length; f++) { modified[f] = Vector3.LerpUnclamped(modified[f], ns.GetPoint(f * stepMult), cis.NormalizeSpeedPercentage); } Frames[v] = modified; yield return(tstack["Normalize speed"].GetInfo(v)); } } clip.MotionPathVertices = null; clip.MotionPathsCount = 0; if (cis.GenerageMotionPaths) { List <Vector3> mPathVertList = new List <Vector3>(); cis.MotionPathsIndexStep = Mathf.Clamp(cis.MotionPathsIndexStep, 1, 1000); for (int v = 0; v < Frames.VerticesCount; v += cis.MotionPathsIndexStep) { for (int f = 0; f < Frames.Count; f++) { mPathVertList.Add(Frames[f, v]); } clip.MotionPathsCount++; yield return(tstack["Generage Motion Paths"].GetInfo(v)); } clip.MotionPathVertices = mPathVertList.ToArray(); } yield return(new TaskInfo("done", 1f)); }