diff --git a/Assets/MMD4UnityTools/Animation/Editor/AnimationHelpers.cs b/Assets/MMD4UnityTools/Animation/Editor/AnimationHelpers.cs new file mode 100644 index 0000000..0a73682 --- /dev/null +++ b/Assets/MMD4UnityTools/Animation/Editor/AnimationHelpers.cs @@ -0,0 +1,137 @@ +using MMDExtensions.Tools; +using System.IO; +using System.Linq; +using UnityEditor; +using UnityEngine; + +namespace MMDExtensions +{ + public class AnimationHelpers + { + #region VMD Methods + + /// + /// Create camera animation assets + /// + [MenuItem("Assets/MMDExtensions/Animation/Create/Camera Animation From VMD")] + public static void CreateCameraAnimation() + { + string path = AssetDatabase.GetAssetPath(Selection.activeObject); + + if (Path.GetExtension(path).ToUpper().Contains("VMD")) + { + var stream = File.Open(path, FileMode.Open); + + var vmd = VMDParser.ParseVMD(stream); + + var orderedFrames = from frame in vmd.Cameras + orderby frame.FrameIndex + select frame; + var animationClip = new AnimationClip() + { + frameRate = 30, + }; + + var delta = 1 / animationClip.frameRate; + var scale = 0.085f;//1.76f / 2f; + + var quaternions = from frame in orderedFrames + select new + { + Time = frame.FrameIndex * delta, + Quaternion = Quaternion.Euler(new Vector3(frame.XRotation * Mathf.Rad2Deg, frame.YRotation * Mathf.Rad2Deg, frame.ZRotation * Mathf.Rad2Deg)), + OutTangent = Mathf.Lerp(-1, 1, frame.Curve.AY / 127), + }; + + var q = quaternions.First().Quaternion; + + var xPosition = from position in orderedFrames + select new Keyframe(position.FrameIndex * delta, position.XPosition * scale); + var YPosition = from position in orderedFrames + select new Keyframe(position.FrameIndex * delta, position.YPosition * scale); + var ZPosition = from position in orderedFrames + select new Keyframe(position.FrameIndex * delta, position.ZPosition * scale); + var XRoation = from quaternion in quaternions + select new Keyframe(quaternion.Time, quaternion.Quaternion.x); + var YRoation = from quaternion in quaternions + select new Keyframe(quaternion.Time, quaternion.Quaternion.y); + var ZRoation = from quaternion in quaternions + select new Keyframe(quaternion.Time, quaternion.Quaternion.z); + var WRoation = from quaternion in quaternions + select new Keyframe(quaternion.Time, quaternion.Quaternion.w); + var fov = from frame in orderedFrames + select new Keyframe(frame.FrameIndex * delta, (float)frame.FOV); + + var xPostionCurve = new AnimationCurve(xPosition.ToArray()); + var yPostionCurve = new AnimationCurve(YPosition.ToArray()); + var zPostionCurve = new AnimationCurve(ZPosition.ToArray()); + var xRotationCurve = new AnimationCurve(XRoation.ToArray()); + var yRotationCurve = new AnimationCurve(YRoation.ToArray()); + var zRotationCurve = new AnimationCurve(ZRoation.ToArray()); + var wRotationCurve = new AnimationCurve(WRoation.ToArray()); + var fovCurve = new AnimationCurve(fov.ToArray()); + animationClip.SetCurve("", typeof(Transform), "localPosition.x", xPostionCurve); + animationClip.SetCurve("", typeof(Transform), "localPosition.y", yPostionCurve); + animationClip.SetCurve("", typeof(Transform), "localPosition.z", zPostionCurve); + animationClip.SetCurve("", typeof(Transform), "localRotation.x", xRotationCurve); + animationClip.SetCurve("", typeof(Transform), "localRotation.y", yRotationCurve); + animationClip.SetCurve("", typeof(Transform), "localRotation.z", zRotationCurve); + animationClip.SetCurve("", typeof(Transform), "localRotation.w", wRotationCurve); + animationClip.SetCurve("", typeof(Camera), "field of view", fovCurve); + + AssetDatabase.CreateAsset(animationClip, path.Replace("vmd", "anim"));//"Assets/VMDCamera.anim"); + } + } + + /// + /// Create morph animation assets + /// + [MenuItem("Assets/MMDExtensions/Animation/Create/Create Morph Animation")] + public static void CreateMorphAnimation() + { + System.GC.Collect(); + string path = AssetDatabase.GetAssetPath(Selection.GetFiltered(SelectionMode.Assets).FirstOrDefault()); + + if (Path.GetExtension(path).ToUpper().Contains("VMD")) + { + var stream = File.Open(path, FileMode.Open); + + var vmd = VMDParser.ParseVMD(stream); + + var animationClip = new AnimationClip() { frameRate = 30 }; + + var delta = 1 / animationClip.frameRate; + + var keyframes = from keys in vmd.Morphs.ToLookup(k => k.MorphName, v => new Keyframe(v.FrameIndex * delta, v.Weight * 100)) + select keys; + + foreach (var package in keyframes) + { + var name = package.Key; + + var curve = new AnimationCurve(package.ToArray()); + var gameobject = Selection.GetFiltered(SelectionMode.TopLevel).FirstOrDefault(); + var gameObjectName = gameobject.name; + var parentName = gameobject.transform.parent.name; + + var mesh = gameobject.GetComponent().sharedMesh; + var bsCounts = mesh.blendShapeCount; + var blendShapeNames = Enumerable.Range(0, bsCounts).ToList().ConvertAll(index => mesh.GetBlendShapeName(index)); + try + { + var registerName = blendShapeNames.Where(x => x.Split('.').Last() == name).First(); + animationClip.SetCurve($"{parentName}/{gameObjectName}", typeof(SkinnedMeshRenderer), $"blendShape.{registerName}", curve); + } + catch + { + continue; + } + } + + AssetDatabase.CreateAsset(animationClip, path.Replace("vmd", "anim")); + } + } + + #endregion VMD Methods + } +} \ No newline at end of file diff --git a/Assets/MMD4UnityTools/Editor/VMDParser.cs b/Assets/MMD4UnityTools/Animation/Editor/VMDParser.cs similarity index 100% rename from Assets/MMD4UnityTools/Editor/VMDParser.cs rename to Assets/MMD4UnityTools/Animation/Editor/VMDParser.cs diff --git a/Assets/MMD4UnityTools/Editor/MMDExtensionsEditor.cs b/Assets/MMD4UnityTools/Material/Editor/MaterialHelpers.cs similarity index 62% rename from Assets/MMD4UnityTools/Editor/MMDExtensionsEditor.cs rename to Assets/MMD4UnityTools/Material/Editor/MaterialHelpers.cs index be49a3a..cd73f7f 100644 --- a/Assets/MMD4UnityTools/Editor/MMDExtensionsEditor.cs +++ b/Assets/MMD4UnityTools/Material/Editor/MaterialHelpers.cs @@ -35,7 +35,7 @@ Set empty texture to null namespace MMDExtensions { - public class MMDExtensionsEditor : Editor + public class MaterialHelpers : Editor { /// /// Upgrade MMD4 materials to HDRP Lit Material, you need to select both pmx and materials @@ -161,8 +161,8 @@ public static void UpgradeABCMaterial() /// /// Create basic HDRP Lit Material from selected textures /// - [MenuItem("Assets/MMDExtensions/Materials/Create/Selected To BaseColor")] - public static void CreateAssetBunldes() + [MenuItem("Assets/MMDExtensions/Materials/Create/Selected As BaseColor")] + public static void SelectedAsBaseColor() { foreach (var file in Selection.GetFiltered(SelectionMode.Assets)) { @@ -172,132 +172,6 @@ public static void CreateAssetBunldes() } } - #region VMD Methods - - /// - /// Create camera animation assets - /// - [MenuItem("Assets/MMDExtensions/Animation/Create/Camera Animation From VMD")] - public static void CreateCameraAnimation() - { - string path = AssetDatabase.GetAssetPath(Selection.activeObject); - - if (Path.GetExtension(path).ToUpper().Contains("VMD")) - { - var stream = File.Open(path, FileMode.Open); - - var vmd = VMDParser.ParseVMD(stream); - - var orderedFrames = from frame in vmd.Cameras - orderby frame.FrameIndex - select frame; - var animationClip = new AnimationClip() - { - frameRate = 30, - }; - - var delta = 1 / animationClip.frameRate; - var scale = 0.085f;//1.76f / 2f; - - var quaternions = from frame in orderedFrames - select new - { - Time = frame.FrameIndex * delta, - Quaternion = Quaternion.Euler(new Vector3(frame.XRotation * Mathf.Rad2Deg, frame.YRotation * Mathf.Rad2Deg, frame.ZRotation * Mathf.Rad2Deg)), - OutTangent = Mathf.Lerp(-1, 1, frame.Curve.AY / 127), - }; - - var q = quaternions.First().Quaternion; - - var xPosition = from position in orderedFrames - select new Keyframe(position.FrameIndex * delta, position.XPosition * scale); - var YPosition = from position in orderedFrames - select new Keyframe(position.FrameIndex * delta, position.YPosition * scale); - var ZPosition = from position in orderedFrames - select new Keyframe(position.FrameIndex * delta, position.ZPosition * scale); - var XRoation = from quaternion in quaternions - select new Keyframe(quaternion.Time, quaternion.Quaternion.x); - var YRoation = from quaternion in quaternions - select new Keyframe(quaternion.Time, quaternion.Quaternion.y); - var ZRoation = from quaternion in quaternions - select new Keyframe(quaternion.Time, quaternion.Quaternion.z); - var WRoation = from quaternion in quaternions - select new Keyframe(quaternion.Time, quaternion.Quaternion.w); - var fov = from frame in orderedFrames - select new Keyframe(frame.FrameIndex * delta, (float)frame.FOV); - - var xPostionCurve = new AnimationCurve(xPosition.ToArray()); - var yPostionCurve = new AnimationCurve(YPosition.ToArray()); - var zPostionCurve = new AnimationCurve(ZPosition.ToArray()); - var xRotationCurve = new AnimationCurve(XRoation.ToArray()); - var yRotationCurve = new AnimationCurve(YRoation.ToArray()); - var zRotationCurve = new AnimationCurve(ZRoation.ToArray()); - var wRotationCurve = new AnimationCurve(WRoation.ToArray()); - var fovCurve = new AnimationCurve(fov.ToArray()); - animationClip.SetCurve("", typeof(Transform), "localPosition.x", xPostionCurve); - animationClip.SetCurve("", typeof(Transform), "localPosition.y", yPostionCurve); - animationClip.SetCurve("", typeof(Transform), "localPosition.z", zPostionCurve); - animationClip.SetCurve("", typeof(Transform), "localRotation.x", xRotationCurve); - animationClip.SetCurve("", typeof(Transform), "localRotation.y", yRotationCurve); - animationClip.SetCurve("", typeof(Transform), "localRotation.z", zRotationCurve); - animationClip.SetCurve("", typeof(Transform), "localRotation.w", wRotationCurve); - animationClip.SetCurve("", typeof(Camera), "field of view", fovCurve); - - AssetDatabase.CreateAsset(animationClip, path.Replace("vmd", "anim"));//"Assets/VMDCamera.anim"); - } - } - - /// - /// Create morph animation assets - /// - [MenuItem("Assets/MMDExtensions/Animation/Create/Create Morph Animation")] - public static void CreateMorphAnimation() - { - System.GC.Collect(); - string path = AssetDatabase.GetAssetPath(Selection.GetFiltered(SelectionMode.Assets).FirstOrDefault()); - - if (Path.GetExtension(path).ToUpper().Contains("VMD")) - { - var stream = File.Open(path, FileMode.Open); - - var vmd = VMDParser.ParseVMD(stream); - - var animationClip = new AnimationClip() { frameRate = 30 }; - - var delta = 1 / animationClip.frameRate; - - var keyframes = from keys in vmd.Morphs.ToLookup(k => k.MorphName, v => new Keyframe(v.FrameIndex * delta, v.Weight * 100)) - select keys; - - foreach (var package in keyframes) - { - var name = package.Key; - - var curve = new AnimationCurve(package.ToArray()); - var gameobject = Selection.GetFiltered(SelectionMode.TopLevel).FirstOrDefault(); - var gameObjectName = gameobject.name; - var parentName = gameobject.transform.parent.name; - - var mesh = gameobject.GetComponent().sharedMesh; - var bsCounts = mesh.blendShapeCount; - var blendShapeNames = Enumerable.Range(0, bsCounts).ToList().ConvertAll(index => mesh.GetBlendShapeName(index)); - try - { - var registerName = blendShapeNames.Where(x => x.Split('.').Last() == name).First(); - animationClip.SetCurve($"{parentName}/{gameObjectName}", typeof(SkinnedMeshRenderer), $"blendShape.{registerName}", curve); - } - catch - { - continue; - } - } - - AssetDatabase.CreateAsset(animationClip, path.Replace("vmd", "anim")); - } - } - - #endregion VMD Methods - #region Helper Methods public static PMX.PMXFormat LoadPmxMaterials(Object @object) diff --git a/Assets/MMD4UnityTools/Editor/StandardPBR2HDRP/CombineTexture.compute b/Assets/MMD4UnityTools/Material/Editor/StandardPBR2HDRP/CombineTexture.compute similarity index 100% rename from Assets/MMD4UnityTools/Editor/StandardPBR2HDRP/CombineTexture.compute rename to Assets/MMD4UnityTools/Material/Editor/StandardPBR2HDRP/CombineTexture.compute diff --git a/Assets/MMD4UnityTools/Editor/StandardPBR2HDRP/StandardPBRTextureTool.cs b/Assets/MMD4UnityTools/Material/Editor/StandardPBR2HDRP/StandardPBRTextureTool.cs similarity index 98% rename from Assets/MMD4UnityTools/Editor/StandardPBR2HDRP/StandardPBRTextureTool.cs rename to Assets/MMD4UnityTools/Material/Editor/StandardPBR2HDRP/StandardPBRTextureTool.cs index 108d05e..f477046 100644 --- a/Assets/MMD4UnityTools/Editor/StandardPBR2HDRP/StandardPBRTextureTool.cs +++ b/Assets/MMD4UnityTools/Material/Editor/StandardPBR2HDRP/StandardPBRTextureTool.cs @@ -12,7 +12,7 @@ public class StandardPBRTextureTool { private static readonly List suffix = new() { "metallic", "ambientOcclusion", "roughness", "OCC", "COLOR", "ROUGH", "SPEC" }; - private const string csPath = "Assets/Editor/MMD4UnityTools/StandardPBR2HDRP/CombineTexture.compute"; + private const string csPath = "Assets/MMD4UnityTools/Material/Editor/StandardPBR2HDRP/CombineTexture.compute"; private static void TransformToPBRMask() { @@ -167,7 +167,7 @@ public static void SaveRTToFile(RenderTexture rt, string path) /// Set standard material to HDRP/Lit shader and map textures to correct slot. /// This will be useful when you create model materials from model importer. /// - [MenuItem("Assets/MMDExtensions/Materials/FromStandardPBR/UpgradeMateirals")] + [MenuItem("Assets/MMDExtensions/Materials/FromStandardPBR/Upgrade Mateirals")] public static void UpgradeMateirals() { var mats = Selection.GetFiltered(SelectionMode.Assets); diff --git a/Assets/MMD4UnityTools/Texture/Editor/TextureCombiner.cs b/Assets/MMD4UnityTools/Texture/Editor/TextureCombiner.cs index 8c333b5..b58f770 100644 --- a/Assets/MMD4UnityTools/Texture/Editor/TextureCombiner.cs +++ b/Assets/MMD4UnityTools/Texture/Editor/TextureCombiner.cs @@ -28,7 +28,7 @@ public class TextureCombinerEditorWindow : EditorWindow [MenuItem("MMDExtensions/Texture/Texture Combiner")] public static void OpenWindow() { - GetWindow("Texture Combiner").Show(); + GetWindow("Texture Combiner").Show(); } private void Combine() @@ -101,22 +101,22 @@ private void OnGUI() { GUILayout.BeginHorizontal(); r = r.ObjectField("R: Metallic", false); - invertR = EditorGUILayout.Toggle(invertR); + invertR = EditorGUILayout.Toggle("Invert R", invertR); GUILayout.EndHorizontal(); GUILayout.BeginHorizontal(); g = g.ObjectField("R: AO", false); - invertG = EditorGUILayout.Toggle(invertG); + invertG = EditorGUILayout.Toggle("Invert G", invertG); GUILayout.EndHorizontal(); GUILayout.BeginHorizontal(); b = b.ObjectField("R: DetailMask", false); - invertB = EditorGUILayout.Toggle(invertB); + invertB = EditorGUILayout.Toggle("Invert B", invertB); GUILayout.EndHorizontal(); GUILayout.BeginHorizontal(); a = a.ObjectField("R: Smoothness", false); - invertA = EditorGUILayout.Toggle(invertA); + invertA = EditorGUILayout.Toggle("Invert A", invertA); GUILayout.EndHorizontal(); if (GUILayout.Button("Combine"))