diff --git a/Editor/Gizmos.meta b/Editor/Gizmos.meta new file mode 100644 index 0000000..6e5f246 --- /dev/null +++ b/Editor/Gizmos.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: e057e650c2af4ea42a1d1b534a8dfbf9 +folderAsset: yes +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Editor/Gizmos/VA_ModelBaker Icon.png b/Editor/Gizmos/VA_ModelBaker Icon.png new file mode 100644 index 0000000..373ebc2 Binary files /dev/null and b/Editor/Gizmos/VA_ModelBaker Icon.png differ diff --git a/Editor/Gizmos/VA_ModelBaker Icon.png.meta b/Editor/Gizmos/VA_ModelBaker Icon.png.meta new file mode 100644 index 0000000..a81e576 --- /dev/null +++ b/Editor/Gizmos/VA_ModelBaker Icon.png.meta @@ -0,0 +1,144 @@ +fileFormatVersion: 2 +guid: 68e0f0fb3c94dae4c8e1d9d8362085b5 +TextureImporter: + internalIDToNameTable: [] + externalObjects: {} + serializedVersion: 11 + mipmaps: + mipMapMode: 0 + enableMipMap: 0 + sRGBTexture: 1 + linearTexture: 0 + fadeOut: 0 + borderMipMap: 0 + mipMapsPreserveCoverage: 0 + alphaTestReferenceValue: 0.5 + mipMapFadeDistanceStart: 1 + mipMapFadeDistanceEnd: 3 + bumpmap: + convertToNormalMap: 0 + externalNormalMap: 0 + heightScale: 0.25 + normalMapFilter: 0 + isReadable: 0 + streamingMipmaps: 0 + streamingMipmapsPriority: 0 + vTOnly: 0 + grayScaleToAlpha: 0 + generateCubemap: 6 + cubemapConvolution: 0 + seamlessCubemap: 0 + textureFormat: 1 + maxTextureSize: 2048 + textureSettings: + serializedVersion: 2 + filterMode: -1 + aniso: 1 + mipBias: -100 + wrapU: 1 + wrapV: 1 + wrapW: 0 + nPOTScale: 0 + lightmap: 0 + compressionQuality: 50 + spriteMode: 0 + spriteExtrude: 1 + spriteMeshType: 1 + alignment: 0 + spritePivot: {x: 0.5, y: 0.5} + spritePixelsToUnits: 100 + spriteBorder: {x: 0, y: 0, z: 0, w: 0} + spriteGenerateFallbackPhysicsShape: 1 + alphaUsage: 1 + alphaIsTransparency: 1 + spriteTessellationDetail: -1 + textureType: 2 + textureShape: 1 + singleChannelComponent: 0 + flipbookRows: 1 + flipbookColumns: 1 + maxTextureSizeSet: 0 + compressionQualitySet: 0 + textureFormatSet: 0 + ignorePngGamma: 0 + applyGammaDecoding: 0 + platformSettings: + - serializedVersion: 3 + buildTarget: DefaultTexturePlatform + maxTextureSize: 8192 + resizeAlgorithm: 0 + textureFormat: -1 + textureCompression: 1 + compressionQuality: 50 + crunchedCompression: 0 + allowsAlphaSplitting: 0 + overridden: 0 + androidETC2FallbackOverride: 0 + forceMaximumCompressionQuality_BC6H_BC7: 0 + - serializedVersion: 3 + buildTarget: Standalone + maxTextureSize: 8192 + resizeAlgorithm: 0 + textureFormat: -1 + textureCompression: 1 + compressionQuality: 50 + crunchedCompression: 0 + allowsAlphaSplitting: 0 + overridden: 0 + androidETC2FallbackOverride: 0 + forceMaximumCompressionQuality_BC6H_BC7: 0 + - serializedVersion: 3 + buildTarget: iPhone + maxTextureSize: 8192 + resizeAlgorithm: 0 + textureFormat: -1 + textureCompression: 1 + compressionQuality: 50 + crunchedCompression: 0 + allowsAlphaSplitting: 0 + overridden: 0 + androidETC2FallbackOverride: 0 + forceMaximumCompressionQuality_BC6H_BC7: 0 + - serializedVersion: 3 + buildTarget: Android + maxTextureSize: 8192 + resizeAlgorithm: 0 + textureFormat: -1 + textureCompression: 1 + compressionQuality: 50 + crunchedCompression: 0 + allowsAlphaSplitting: 0 + overridden: 0 + androidETC2FallbackOverride: 0 + forceMaximumCompressionQuality_BC6H_BC7: 0 + - serializedVersion: 3 + buildTarget: Windows Store Apps + maxTextureSize: 8192 + resizeAlgorithm: 0 + textureFormat: -1 + textureCompression: 1 + compressionQuality: 50 + crunchedCompression: 0 + allowsAlphaSplitting: 0 + overridden: 0 + androidETC2FallbackOverride: 0 + forceMaximumCompressionQuality_BC6H_BC7: 0 + spriteSheet: + serializedVersion: 2 + sprites: [] + outline: [] + physicsShape: [] + bones: [] + spriteID: + internalID: 0 + vertices: [] + indices: + edges: [] + weights: [] + secondaryTextures: [] + spritePackingTag: + pSDRemoveMatte: 0 + pSDShowRemoveMatteOption: 0 + userData: + assetBundleName: + assetBundleVariant: diff --git a/Editor/Scripts/Editor/ModelBaker.meta b/Editor/Scripts/Editor/ModelBaker.meta new file mode 100644 index 0000000..9815468 --- /dev/null +++ b/Editor/Scripts/Editor/ModelBaker.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: afa9933157fe17b40be247abddb0b2ee +folderAsset: yes +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Editor/Scripts/Editor/ModelBaker/Editor.meta b/Editor/Scripts/Editor/ModelBaker/Editor.meta new file mode 100644 index 0000000..9f556f6 --- /dev/null +++ b/Editor/Scripts/Editor/ModelBaker/Editor.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: 5fb7e85d011f3c6419742e766fc11aeb +folderAsset: yes +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Editor/Scripts/Editor/ModelBaker/Editor/VA_ModelBakerEditor.cs b/Editor/Scripts/Editor/ModelBaker/Editor/VA_ModelBakerEditor.cs new file mode 100644 index 0000000..c3ddfa3 --- /dev/null +++ b/Editor/Scripts/Editor/ModelBaker/Editor/VA_ModelBakerEditor.cs @@ -0,0 +1,109 @@ +using UnityEngine; +using UnityEditor; + +namespace TAO.VertexAnimation.Editor +{ + [CustomEditor(typeof(VA_ModelBaker))] + public class VA_ModelBakerEditor : UnityEditor.Editor + { + private VA_ModelBaker modelBaker = null; + + void OnEnable() + { + modelBaker = target as VA_ModelBaker; + } + + public override void OnInspectorGUI() + { + serializedObject.Update(); + + InputGUI(); + BakeGUI(); + OutputGUI(); + + serializedObject.ApplyModifiedProperties(); + } + + private void InputGUI() + { + //public GameObject model; + //public AnimationClip[] animationClips; + //public int fps = 24; + //public int textureWidth = 512; + //public bool saveBakedDataToAsset = true; + //public bool generateAnimationBook = false; + + EditorGUILayout.PropertyField(serializedObject.FindProperty("model")); + EditorGUILayout.PropertyField(serializedObject.FindProperty("animationClips")); + EditorGUILayout.PropertyField(serializedObject.FindProperty("fps")); + EditorGUILayout.PropertyField(serializedObject.FindProperty("textureWidth")); + EditorGUILayout.PropertyField(serializedObject.FindProperty("saveBakedDataToAsset")); + EditorGUILayout.PropertyField(serializedObject.FindProperty("generateAnimationBook")); + } + + private void BakeGUI() + { + if (GUILayout.Button("Bake")) + { + ClearBakedData(); + + modelBaker.Bake(); + + if (modelBaker.saveBakedDataToAsset) + { + SaveBakedData(); + } + } + + using (new EditorGUILayout.HorizontalScope()) + { + if (GUILayout.Button("SaveBakedData", EditorStyles.miniButtonLeft)) + { + SaveBakedData(); + } + + if (GUILayout.Button("ClearBakedData", EditorStyles.miniButtonRight)) + { + ClearBakedData(); + } + } + } + + private void OutputGUI() + { + using (new EditorGUI.DisabledGroupScope(true)) + { + EditorGUILayout.PropertyField(serializedObject.FindProperty("bakedData")); + } + } + + private void SaveBakedData() + { + AssetDatabase.AddObjectToAsset(modelBaker.BakedData.mesh, modelBaker); + + foreach (var pm in modelBaker.BakedData.positionMaps) + { + AssetDatabase.AddObjectToAsset(pm, modelBaker); + } + + AssetDatabase.SaveAssets(); + AssetDatabase.Refresh(); + } + + private void ClearBakedData() + { + var assets = AssetDatabase.LoadAllAssetsAtPath(AssetDatabase.GetAssetPath(modelBaker)); + + foreach (var a in assets) + { + if (a != modelBaker) + { + AssetDatabase.RemoveObjectFromAsset(a); + } + } + + AssetDatabase.SaveAssets(); + AssetDatabase.Refresh(); + } + } +} diff --git a/Editor/Scripts/Editor/ModelBaker/Editor/VA_ModelBakerEditor.cs.meta b/Editor/Scripts/Editor/ModelBaker/Editor/VA_ModelBakerEditor.cs.meta new file mode 100644 index 0000000..f0f745e --- /dev/null +++ b/Editor/Scripts/Editor/ModelBaker/Editor/VA_ModelBakerEditor.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: 3a3231c3c369f0c4ab95f98b979d0530 +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Editor/Scripts/VA_AssetConverter.cs b/Editor/Scripts/VA_AssetConverter.cs new file mode 100644 index 0000000..4b5c5c8 --- /dev/null +++ b/Editor/Scripts/VA_AssetConverter.cs @@ -0,0 +1,12 @@ +using System.Collections; +using System.Collections.Generic; +using UnityEngine; + +namespace TAO.VertexAnimation.Editor +{ + [CreateAssetMenu(fileName = "new AssetConverter", menuName = "VA_Animation/AssetConverter", order = 400)] + public class VA_AssetConverter : ScriptableObject + { + + } +} diff --git a/Editor/Scripts/VA_AssetConverter.cs.meta b/Editor/Scripts/VA_AssetConverter.cs.meta new file mode 100644 index 0000000..a364a38 --- /dev/null +++ b/Editor/Scripts/VA_AssetConverter.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: 55b196764521c964c84e8f2edd5c8da5 +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Runtime/Scripts/ModelBaker.meta b/Runtime/Scripts/ModelBaker.meta new file mode 100644 index 0000000..0eba146 --- /dev/null +++ b/Runtime/Scripts/ModelBaker.meta @@ -0,0 +1,8 @@ +fileFormatVersion: 2 +guid: 657facf5ba53f664b95d329ffb58abb1 +folderAsset: yes +DefaultImporter: + externalObjects: {} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Runtime/Scripts/ModelBaker/AnimationBaker.cs b/Runtime/Scripts/ModelBaker/AnimationBaker.cs new file mode 100644 index 0000000..d90fb13 --- /dev/null +++ b/Runtime/Scripts/ModelBaker/AnimationBaker.cs @@ -0,0 +1,189 @@ +using System.Collections.Generic; +using UnityEngine; + +namespace TAO.VertexAnimation +{ + public static class AnimationBaker + { + [System.Serializable] + public struct BakedData + { + public Mesh mesh; + public List positionMaps; + + // Returns main position map. + public Texture2D GetPositionMap + { + get + { + return positionMaps[0]; + } + } + } + + [System.Serializable] + public struct AnimationInfo + { + public int rawFrameHeight; + public int frameHeight; + public int frameSpacing; + public int frames; + public int maxFrames; + public int textureWidth; + public int textureHeight; + + // Create animation info and calculate values. + public AnimationInfo(Mesh mesh, int frames, int textureWidth) + { + this.frames = frames; + this.textureWidth = textureWidth; + + rawFrameHeight = Mathf.CeilToInt((float)mesh.vertices.Length / this.textureWidth); + frameHeight = Mathf.NextPowerOfTwo(rawFrameHeight); + frameSpacing = (frameHeight - rawFrameHeight) + 1; + + textureHeight = Mathf.NextPowerOfTwo(frameHeight * this.frames); + + maxFrames = textureHeight / frameHeight; + } + } + + public static BakedData Bake(this GameObject model, AnimationClip[] animationClips, int fps, int textureWidth) + { + BakedData bakedData = new BakedData() + { + mesh = null, + positionMaps = new List() + }; + + // Calculate what our max frames/time is going to be. + int maxFrames = 0; + foreach (AnimationClip ac in animationClips) + { + int frames = Mathf.FloorToInt(fps * ac.length); + + if (maxFrames < frames) + { + maxFrames = frames; + } + } + + // Get the target mesh to calculate the animation info. + Mesh mesh = model.GetComponent().sharedMesh; + + // Get the info for the biggest animation. + AnimationInfo animationInfo = new AnimationInfo(mesh, maxFrames, textureWidth); + + foreach (AnimationClip ac in animationClips) + { + // Set the frames for this animation. + animationInfo.frames = Mathf.FloorToInt(fps * ac.length); + + BakedData bd = Bake(model, ac, animationInfo); + bakedData.mesh = bd.mesh; + bakedData.positionMaps.AddRange(bd.positionMaps); + } + + return bakedData; + } + + public static BakedData Bake(this GameObject model, AnimationClip animationClip, AnimationInfo animationInfo) + { + Mesh mesh = new Mesh + { + name = string.Format("{0}", model.name) + }; + + // Bake mesh for a copy and to apply the new UV's to. + SkinnedMeshRenderer skinnedMeshRenderer = model.GetComponent(); + skinnedMeshRenderer.BakeMesh(mesh); + mesh.RecalculateBounds(); + + mesh.uv3 = mesh.BakePositionUVs(animationInfo); + + BakedData bakedData = new BakedData() + { + mesh = mesh, + positionMaps = new List() { BakePositionMap(model, animationClip, animationInfo) } + }; + + return bakedData; + } + + public static Texture2D BakePositionMap(this GameObject model, AnimationClip animationClip, AnimationInfo animationInfo) + { + // Create positionMap Texture without MipMaps which is Linear and HDR to store values in a bigger range. + Texture2D positionMap = new Texture2D(animationInfo.textureWidth, animationInfo.textureHeight, TextureFormat.RGBAHalf, false, true); + + // Create instance to sample from. + GameObject inst = GameObject.Instantiate(model); + SkinnedMeshRenderer skinnedMeshRenderer = inst.GetComponent(); + + int y = 0; + for (int f = 0; f < animationInfo.frames; f++) + { + animationClip.SampleAnimation(inst, (animationClip.length / animationInfo.frames) * f); + + Mesh sampledMesh = new Mesh(); + skinnedMeshRenderer.BakeMesh(sampledMesh); + sampledMesh.RecalculateBounds(); + + int x = 0; + for (int v = 0; v < sampledMesh.vertices.Length; v++) + { + Vector3 vert = sampledMesh.vertices[v]; + Vector3 normal = sampledMesh.normals[v]; + + positionMap.SetPixel(x, y, + new Color(vert.x, vert.y, vert.z, + VectorUtils.Float3ToFloat(normal)) + ); + + x++; + if (x >= animationInfo.textureWidth) + { + x = 0; + y++; + } + } + y += animationInfo.frameSpacing; + } + + GameObject.DestroyImmediate(inst); + + positionMap.name = string.Format("VA_N-{0}_F-{1}_MF-{2}", animationClip.name, animationInfo.frames, animationInfo.maxFrames); + positionMap.filterMode = FilterMode.Point; + // TODO: Make no longer readable. + positionMap.Apply(false, false); + + return positionMap; + } + + public static Vector2[] BakePositionUVs(this Mesh mesh, AnimationInfo animationInfo) + { + Vector2[] uv3 = new Vector2[mesh.vertices.Length]; + + float xOffset = 1.0f / animationInfo.textureWidth; + float yOffset = 1.0f / animationInfo.textureHeight; + + float x = xOffset / 2.0f; + float y = yOffset / 2.0f; + + for (int v = 0; v < mesh.vertices.Length; v++) + { + uv3[v] = new Vector2(x, y); + + x += xOffset; + if (x >= 1.0f) + { + x = xOffset / 2.0f; + y += yOffset; + } + } + + mesh.uv3 = uv3; + + return uv3; + } + } +} \ No newline at end of file diff --git a/Runtime/Scripts/ModelBaker/AnimationBaker.cs.meta b/Runtime/Scripts/ModelBaker/AnimationBaker.cs.meta new file mode 100644 index 0000000..b427242 --- /dev/null +++ b/Runtime/Scripts/ModelBaker/AnimationBaker.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: f73c308e347c32142b0f61e8b2550914 +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Runtime/Scripts/ModelBaker/MeshCombiner.cs b/Runtime/Scripts/ModelBaker/MeshCombiner.cs new file mode 100644 index 0000000..1f0192e --- /dev/null +++ b/Runtime/Scripts/ModelBaker/MeshCombiner.cs @@ -0,0 +1,254 @@ +// References: +// https://forum.unity.com/threads/help-combining-and-manipulating-skinned-mesh-renderers-imported-from-blender.505078/ +// http://wiki.unity3d.com/index.php/CombineSkinnedMeshes +// http://wiki.unity3d.com/index.php/SkinnedMeshCombiner + +// TODO: +// ---Bake ALL the MeshRenderers/SkinnedMeshRenderers and merge them together.--- +// ---Bake multiple animations.--- +// ---Get the longest animation to calculate the texture height, so all the textures have the same height for the 3D texture.--- +// Add options and previews for texture size, animation phasing/fps. +// Either merge with the animation books or generate them from this and maybe store them as child (and then don't destroy them on re-bake to keep the reference but replace it). + +using UnityEngine; +using System.Collections.Generic; +using System.Linq; + +namespace TAO.VertexAnimation +{ + public static class MeshCombiner + { + private struct MaterialMeshGroup + { + public List skinnedMeshes; + public List<(MeshFilter mf, MeshRenderer mr)> meshes; + public Material material; + } + + public static SkinnedMeshRenderer Combine(this SkinnedMeshRenderer target, List skinnedMeshes, List<(MeshFilter mf, MeshRenderer mr)> meshes) + { + List groups = new List(); + + // Group skinnedMeshes. + foreach (var sm in skinnedMeshes) + { + bool hasGroup = false; + foreach (var g in groups) + { + if (sm.sharedMaterial == g.material) + { + hasGroup = true; + g.skinnedMeshes.Add(sm); + } + } + + if (!hasGroup) + { + groups.Add(new MaterialMeshGroup() + { + skinnedMeshes = new List() + { + sm + }, + meshes = new List<(MeshFilter mf, MeshRenderer mr)>(), + material = sm.sharedMaterial + }); + } + } + + // Group Meshes. + foreach (var m in meshes) + { + bool hasGroup = false; + foreach (var g in groups) + { + if (m.mr.sharedMaterial == g.material) + { + hasGroup = true; + g.meshes.Add(m); + } + } + + if (!hasGroup) + { + groups.Add(new MaterialMeshGroup() + { + skinnedMeshes = new List(), + meshes = new List<(MeshFilter mf, MeshRenderer mr)>() + { + m + }, + material = m.mr.sharedMaterial + }); + } + } + + List tmp = new List(); + for (int i = 0; i < groups.Count; i++) + { + tmp.Add(new GameObject("tmpChild", typeof(SkinnedMeshRenderer))); + tmp[i].transform.parent = target.transform; + + MaterialMeshGroup mmg = groups[i]; + tmp[i].GetComponent().Combine(mmg.skinnedMeshes, mmg.meshes, mmg.material); + } + + // TODO: Merge materialMergedObjects. + // TEMP: Remove when materialMergedObjects. + SkinnedMeshRenderer newSkinnedMeshRenderer = tmp[0].GetComponent(); + target.sharedMesh = newSkinnedMeshRenderer.sharedMesh; + target.sharedMaterial = newSkinnedMeshRenderer.sharedMaterial; + target.bones = newSkinnedMeshRenderer.bones; + + foreach (var go in tmp) + { + GameObject.DestroyImmediate(go); + } + + // Set a name to make it more clear. + target.sharedMesh.name = target.transform.name.Replace("(Clone)", ""); + return target; + } + + public static SkinnedMeshRenderer Combine(this SkinnedMeshRenderer target, List skinnedMeshes, List<(MeshFilter mf, MeshRenderer mr)> meshes, Material mainMaterial) + { + List bones = new List(); + List boneWeights = new List(); + List bindPoses = new List(); + List combineInstances = new List(); + + // Combine SkinnedMeshes. + int boneOffset = 0; + for (int s = 0; s < skinnedMeshes.Count; s++) + { + SkinnedMeshRenderer smr = skinnedMeshes[s]; + + //if the skinned mesh renderer has a material other than the default + //we assume it's a one-off face material and deal with it later + if (smr.sharedMaterial != mainMaterial) + { + continue; + } + + BoneWeight[] meshBoneweight = smr.sharedMesh.boneWeights; + + // May want to modify this if the renderer shares bones as unnecessary bones will get added. + // We don't care since it is going to be converted into vertex animations later anyways. + for (int i = 0; i < meshBoneweight.Length; ++i) + { + BoneWeight bWeight = meshBoneweight[i]; + + bWeight.boneIndex0 += boneOffset; + bWeight.boneIndex1 += boneOffset; + bWeight.boneIndex2 += boneOffset; + bWeight.boneIndex3 += boneOffset; + + boneWeights.Add(bWeight); + } + + boneOffset += smr.bones.Length; + + Transform[] meshBones = smr.bones; + for (int i = 0; i < meshBones.Length; ++i) + { + bones.Add(meshBones[i]); + + //we take the old bind pose that mapped from our mesh to world to bone, + //and take out our localToWorldMatrix, so now it's JUST the bone matrix + //since our skinned mesh renderer is going to be on the root of our object that works + bindPoses.Add(smr.sharedMesh.bindposes[i] * smr.transform.worldToLocalMatrix); + } + + CombineInstance ci = new CombineInstance + { + mesh = smr.sharedMesh, + transform = smr.transform.localToWorldMatrix + }; + combineInstances.Add(ci); + + GameObject.DestroyImmediate(smr); + } + + // Combine Meshes. + for (int s = 0; meshes != null && s < meshes.Count; s++) + { + MeshFilter filter = meshes[s].mf; + MeshRenderer renderer = meshes[s].mr; + + //if the skinned mesh renderer has a material other than the default + //we assume it's a one-off face material and deal with it later + if (renderer.sharedMaterial != mainMaterial) + { + continue; + } + + // May want to modify this if the renderer shares bones as unnecessary bones will get added. + // We don't care since it is going to be converted into vertex animations later anyways. + int vertCount = filter.sharedMesh.vertexCount; + for (int i = 0; i < vertCount; ++i) + { + BoneWeight bWeight = new BoneWeight + { + boneIndex0 = boneOffset, + boneIndex1 = boneOffset, + boneIndex2 = boneOffset, + boneIndex3 = boneOffset, + weight0 = 1 + }; + + boneWeights.Add(bWeight); + } + + boneOffset += 1; + + bones.Add(filter.transform); + + // TODO: figure out what this should be. + bindPoses.Add(filter.transform.worldToLocalMatrix); + + CombineInstance ci = new CombineInstance + { + mesh = filter.sharedMesh, + transform = filter.transform.localToWorldMatrix + }; + combineInstances.Add(ci); + + GameObject.DestroyImmediate(filter); + GameObject.DestroyImmediate(renderer); + } + + // Actually combine and recalculate mesh. + Mesh skinnedMesh = new Mesh(); + skinnedMesh.CombineMeshes(combineInstances.ToArray(), true, true); + skinnedMesh.RecalculateBounds(); + + // Copy settings to target. + target.sharedMesh = skinnedMesh; + target.sharedMaterial = mainMaterial; + target.bones = bones.ToArray(); + target.sharedMesh.boneWeights = boneWeights.ToArray(); + target.sharedMesh.bindposes = bindPoses.ToArray(); + + return target; + } + + public static void ConbineAndConvertGameObject(this GameObject gameObject) + { + // Get Skinned Meshes. + List skinnedMeshes = gameObject.GetComponentsInChildren(true).ToList(); + // Get Meshes. + List<(MeshFilter, MeshRenderer)> meshes = new List<(MeshFilter, MeshRenderer)>(); + foreach (var mf in gameObject.GetComponentsInChildren(true)) + { + if (mf.TryGetComponent(out MeshRenderer mr)) + { + meshes.Add((mf, mr)); + } + } + + // Add target mesh. + SkinnedMeshRenderer target = gameObject.AddComponent(); + target.Combine(skinnedMeshes, meshes); + } + } +} \ No newline at end of file diff --git a/Runtime/Scripts/ModelBaker/MeshCombiner.cs.meta b/Runtime/Scripts/ModelBaker/MeshCombiner.cs.meta new file mode 100644 index 0000000..3ba9ac3 --- /dev/null +++ b/Runtime/Scripts/ModelBaker/MeshCombiner.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: f43224daff50a5042a182c6fb12440a8 +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Runtime/Scripts/ModelBaker/VA_ModelBaker.cs b/Runtime/Scripts/ModelBaker/VA_ModelBaker.cs new file mode 100644 index 0000000..bfddaf4 --- /dev/null +++ b/Runtime/Scripts/ModelBaker/VA_ModelBaker.cs @@ -0,0 +1,37 @@ +using System.Collections; +using System.Collections.Generic; +using UnityEngine; + +namespace TAO.VertexAnimation +{ + [CreateAssetMenu(fileName = "new ModelBaker", menuName = "VA_ModelBaker/ModelBaker", order = 400)] + public class VA_ModelBaker : ScriptableObject + { + public GameObject model; + public AnimationClip[] animationClips; + public int fps = 24; + public int textureWidth = 512; + public bool saveBakedDataToAsset = true; + public bool generateAnimationBook = false; + + [SerializeField] + private AnimationBaker.BakedData bakedData; + public AnimationBaker.BakedData BakedData + { + get + { + return bakedData; + } + } + + public void Bake() + { + var target = Instantiate(model); + + target.ConbineAndConvertGameObject(); + bakedData = target.Bake(animationClips, fps, textureWidth); + + DestroyImmediate(target); + } + } +} \ No newline at end of file diff --git a/Runtime/Scripts/ModelBaker/VA_ModelBaker.cs.meta b/Runtime/Scripts/ModelBaker/VA_ModelBaker.cs.meta new file mode 100644 index 0000000..0ecd82b --- /dev/null +++ b/Runtime/Scripts/ModelBaker/VA_ModelBaker.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: 6752e365d065458469473b601e74e699 +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Runtime/Scripts/ModelBaker/VectorUtils.cs b/Runtime/Scripts/ModelBaker/VectorUtils.cs new file mode 100644 index 0000000..09fa5fe --- /dev/null +++ b/Runtime/Scripts/ModelBaker/VectorUtils.cs @@ -0,0 +1,34 @@ +using UnityEngine; + +namespace TAO.VertexAnimation +{ + public static class VectorUtils + { + public static Vector2 Float3ToFloat2(this Vector3 f3) + { + Vector3 rotation = Vector3.Normalize(new Vector3(f3.x, 0, f3.z)); + + Vector2 f2 = new Vector2(); + f2.x = Mathf.Acos(Vector3.Dot(rotation, new Vector3(1, 0, 0))) * Mathf.Sign(f3.z); + f2.x = ((f2.x / Mathf.PI) + 1) * 0.5f; + + f2.y = Mathf.Acos(f3.y) / Mathf.PI; + + f2 *= 15; + f2.x = Mathf.Round(f2.x); + f2.y = Mathf.Round(f2.y); + + return f2; + } + + public static float Float2ToFloat(this Vector2 f2) + { + return (f2.x + (16 * f2.y)) / 255; + } + + public static float Float3ToFloat(this Vector3 f3) + { + return Float2ToFloat(Float3ToFloat2(f3)); + } + } +} \ No newline at end of file diff --git a/Runtime/Scripts/ModelBaker/VectorUtils.cs.meta b/Runtime/Scripts/ModelBaker/VectorUtils.cs.meta new file mode 100644 index 0000000..81cbd58 --- /dev/null +++ b/Runtime/Scripts/ModelBaker/VectorUtils.cs.meta @@ -0,0 +1,11 @@ +fileFormatVersion: 2 +guid: 0a4c82d2f184d3f4d8bb111e89009c3f +MonoImporter: + externalObjects: {} + serializedVersion: 2 + defaultReferences: [] + executionOrder: 0 + icon: {instanceID: 0} + userData: + assetBundleName: + assetBundleVariant: diff --git a/Runtime/Shaders/HLSL/VertexAnimation.hlsl b/Runtime/Shaders/HLSL/VertexAnimation.hlsl index c1e778f..7e9561d 100644 --- a/Runtime/Shaders/HLSL/VertexAnimation.hlsl +++ b/Runtime/Shaders/HLSL/VertexAnimation.hlsl @@ -20,6 +20,21 @@ float2 VA_UV_float(float2 uv, int maxFrames, float time) return uvPosition; } +float2 VA1_UV_float(float2 uv, int maxFrames, float time) +{ + float2 uvPosition; + + float timeInFrames = frac(time); + timeInFrames = ceil(timeInFrames * maxFrames); + timeInFrames /= maxFrames; + timeInFrames += round(1.0f / maxFrames); + + uvPosition.x = uv.x; + uvPosition.y = (1.0f - (1.0f - uv.y) - (1.0f - (timeInFrames))); + + return uvPosition; +} + void VA_float(float2 uv, SamplerState texSampler, Texture2D positionMap, float time, int maxFrames, out float3 position, out float3 alpha) { @@ -34,6 +49,20 @@ void VA_float(float2 uv, SamplerState texSampler, Texture2D positionMap, float t alpha = texturePos.w; } +void VA1_float(float2 uv, SamplerState texSampler, Texture2D positionMap, float time, int maxFrames, + out float3 position, out float alpha) +{ + float2 uvPosition = VA1_UV_float(uv, maxFrames, time); + + // Position. + float4 texturePos = positionMap.SampleLevel(texSampler, uvPosition, 0); + position = texturePos.xyz; + + // Normal. + //FloatToFloat3_float(texturePos.w, outNormal); + alpha = texturePos.w; +} + void VA_ARRAY_float(float2 uv, SamplerState texSampler, Texture2DArray positionMap, float positionMapIndex, float time, int maxFrames, out float3 position, out float3 alpha) { diff --git a/Runtime/Shaders/SubGraphs/VA1.shadersubgraph b/Runtime/Shaders/SubGraphs/VA1.shadersubgraph new file mode 100644 index 0000000..339f271 --- /dev/null +++ b/Runtime/Shaders/SubGraphs/VA1.shadersubgraph @@ -0,0 +1,799 @@ +{ + "m_SGVersion": 2, + "m_Type": "UnityEditor.ShaderGraph.GraphData", + "m_ObjectId": "144dcb1a2d15470a91360080bc9bd989", + "m_Properties": [ + { + "m_Id": "3564f72314574212a0eed0f9581a6b85" + }, + { + "m_Id": "a09a6ce7e08545d99b5bda70586f4e79" + }, + { + "m_Id": "975a04061f8d4786bce18d1574108732" + }, + { + "m_Id": "f9b649ed28584dca8a522f3fb582f350" + }, + { + "m_Id": "967e0c2bcb6e48c2b85b82c6d4c734a4" + } + ], + "m_Keywords": [], + "m_Nodes": [ + { + "m_Id": "031d019a3f114a639fed0a731159883c" + }, + { + "m_Id": "83aca69ecbd845e888867dea88a660f1" + }, + { + "m_Id": "46dfe2d873b3436a89d174ac3545bc00" + }, + { + "m_Id": "f39a0ab1ea5d4129b8c210c762bed693" + }, + { + "m_Id": "5c18cb5e2e0542c2ae766d7de7011cda" + }, + { + "m_Id": "431f7271c3544d459b5128258fd524ed" + }, + { + "m_Id": "bc36bc83631c44e0b48e951b444ba971" + } + ], + "m_GroupDatas": [], + "m_StickyNoteDatas": [], + "m_Edges": [ + { + "m_OutputSlot": { + "m_Node": { + "m_Id": "431f7271c3544d459b5128258fd524ed" + }, + "m_SlotId": 0 + }, + "m_InputSlot": { + "m_Node": { + "m_Id": "83aca69ecbd845e888867dea88a660f1" + }, + "m_SlotId": 4 + } + }, + { + "m_OutputSlot": { + "m_Node": { + "m_Id": "46dfe2d873b3436a89d174ac3545bc00" + }, + "m_SlotId": 0 + }, + "m_InputSlot": { + "m_Node": { + "m_Id": "83aca69ecbd845e888867dea88a660f1" + }, + "m_SlotId": 0 + } + }, + { + "m_OutputSlot": { + "m_Node": { + "m_Id": "5c18cb5e2e0542c2ae766d7de7011cda" + }, + "m_SlotId": 0 + }, + "m_InputSlot": { + "m_Node": { + "m_Id": "83aca69ecbd845e888867dea88a660f1" + }, + "m_SlotId": 2 + } + }, + { + "m_OutputSlot": { + "m_Node": { + "m_Id": "83aca69ecbd845e888867dea88a660f1" + }, + "m_SlotId": 9 + }, + "m_InputSlot": { + "m_Node": { + "m_Id": "031d019a3f114a639fed0a731159883c" + }, + "m_SlotId": 1 + } + }, + { + "m_OutputSlot": { + "m_Node": { + "m_Id": "83aca69ecbd845e888867dea88a660f1" + }, + "m_SlotId": 10 + }, + "m_InputSlot": { + "m_Node": { + "m_Id": "031d019a3f114a639fed0a731159883c" + }, + "m_SlotId": 2 + } + }, + { + "m_OutputSlot": { + "m_Node": { + "m_Id": "bc36bc83631c44e0b48e951b444ba971" + }, + "m_SlotId": 0 + }, + "m_InputSlot": { + "m_Node": { + "m_Id": "83aca69ecbd845e888867dea88a660f1" + }, + "m_SlotId": 6 + } + }, + { + "m_OutputSlot": { + "m_Node": { + "m_Id": "f39a0ab1ea5d4129b8c210c762bed693" + }, + "m_SlotId": 0 + }, + "m_InputSlot": { + "m_Node": { + "m_Id": "83aca69ecbd845e888867dea88a660f1" + }, + "m_SlotId": 1 + } + } + ], + "m_VertexContext": { + "m_Position": { + "x": 0.0, + "y": 0.0 + }, + "m_Blocks": [] + }, + "m_FragmentContext": { + "m_Position": { + "x": 0.0, + "y": 0.0 + }, + "m_Blocks": [] + }, + "m_PreviewData": { + "serializedMesh": { + "m_SerializedMesh": "{\"mesh\":{\"instanceID\":0}}", + "m_Guid": "" + } + }, + "m_Path": "Sub Graphs", + "m_ConcretePrecision": 0, + "m_OutputNode": { + "m_Id": "031d019a3f114a639fed0a731159883c" + }, + "m_ActiveTargets": [] +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.SubGraphOutputNode", + "m_ObjectId": "031d019a3f114a639fed0a731159883c", + "m_Group": { + "m_Id": "" + }, + "m_Name": "Output", + "m_DrawState": { + "m_Expanded": true, + "m_Position": { + "serializedVersion": "2", + "x": -108.0, + "y": -144.0, + "width": 120.0, + "height": 77.0 + } + }, + "m_Slots": [ + { + "m_Id": "b89a68670a6642e19ae1063415132848" + }, + { + "m_Id": "ad82a5146c4a46cc98b02a7e412b84b9" + } + ], + "synonyms": [], + "m_Precision": 0, + "m_PreviewExpanded": true, + "m_CustomColors": { + "m_SerializableColors": [] + }, + "IsFirstSlotValid": true +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.Vector1MaterialSlot", + "m_ObjectId": "23a471ed9f794edb8e8bd66a5f65451e", + "m_Id": 0, + "m_DisplayName": "Time", + "m_SlotType": 1, + "m_Hidden": false, + "m_ShaderOutputName": "Out", + "m_StageCapability": 3, + "m_Value": 0.0, + "m_DefaultValue": 0.0, + "m_Labels": [ + "X" + ] +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.Internal.Texture2DShaderProperty", + "m_ObjectId": "3564f72314574212a0eed0f9581a6b85", + "m_Guid": { + "m_GuidSerialized": "7a6985bf-76e4-4794-ab89-d013bd6b7c48" + }, + "m_Name": "PositionMap", + "m_DefaultReferenceName": "Texture2D_3564f72314574212a0eed0f9581a6b85", + "m_OverrideReferenceName": "", + "m_GeneratePropertyBlock": true, + "m_Precision": 0, + "overrideHLSLDeclaration": false, + "hlslDeclarationOverride": 0, + "m_Hidden": false, + "m_Value": { + "m_SerializedTexture": "{\"texture\":{\"instanceID\":0}}", + "m_Guid": "" + }, + "m_Modifiable": true, + "m_DefaultType": 0 +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.SamplerStateMaterialSlot", + "m_ObjectId": "3e7d4ea371804f5c9265e859f8e8e08b", + "m_Id": 1, + "m_DisplayName": "texSampler", + "m_SlotType": 0, + "m_Hidden": false, + "m_ShaderOutputName": "texSampler", + "m_StageCapability": 3 +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.PropertyNode", + "m_ObjectId": "431f7271c3544d459b5128258fd524ed", + "m_Group": { + "m_Id": "" + }, + "m_Name": "Property", + "m_DrawState": { + "m_Expanded": true, + "m_Position": { + "serializedVersion": "2", + "x": -546.0, + "y": -32.0, + "width": 102.0, + "height": 34.0 + } + }, + "m_Slots": [ + { + "m_Id": "23a471ed9f794edb8e8bd66a5f65451e" + } + ], + "synonyms": [], + "m_Precision": 0, + "m_PreviewExpanded": true, + "m_CustomColors": { + "m_SerializableColors": [] + }, + "m_Property": { + "m_Id": "f9b649ed28584dca8a522f3fb582f350" + } +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.PropertyNode", + "m_ObjectId": "46dfe2d873b3436a89d174ac3545bc00", + "m_Group": { + "m_Id": "" + }, + "m_Name": "Property", + "m_DrawState": { + "m_Expanded": true, + "m_Position": { + "serializedVersion": "2", + "x": -544.0, + "y": -104.0, + "width": 93.0, + "height": 34.0 + } + }, + "m_Slots": [ + { + "m_Id": "91fad60529a14d678005224cfbac1b50" + } + ], + "synonyms": [], + "m_Precision": 0, + "m_PreviewExpanded": true, + "m_CustomColors": { + "m_SerializableColors": [] + }, + "m_Property": { + "m_Id": "a09a6ce7e08545d99b5bda70586f4e79" + } +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.SamplerStateMaterialSlot", + "m_ObjectId": "4820d64a797d4948a129f455b98feed8", + "m_Id": 0, + "m_DisplayName": "SamplerState", + "m_SlotType": 1, + "m_Hidden": false, + "m_ShaderOutputName": "Out", + "m_StageCapability": 3 +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.Vector1MaterialSlot", + "m_ObjectId": "5ae3156d60f846c68b9b446bc239bbea", + "m_Id": 10, + "m_DisplayName": "alpha", + "m_SlotType": 1, + "m_Hidden": false, + "m_ShaderOutputName": "alpha", + "m_StageCapability": 3, + "m_Value": 0.0, + "m_DefaultValue": 0.0, + "m_Labels": [] +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.PropertyNode", + "m_ObjectId": "5c18cb5e2e0542c2ae766d7de7011cda", + "m_Group": { + "m_Id": "" + }, + "m_Name": "Property", + "m_DrawState": { + "m_Expanded": true, + "m_Position": { + "serializedVersion": "2", + "x": -594.0, + "y": -56.0, + "width": 151.0, + "height": 34.0 + } + }, + "m_Slots": [ + { + "m_Id": "ffcaa3e5c6a5468c92d6d08c301a6f59" + } + ], + "synonyms": [], + "m_Precision": 0, + "m_PreviewExpanded": true, + "m_CustomColors": { + "m_SerializableColors": [] + }, + "m_Property": { + "m_Id": "3564f72314574212a0eed0f9581a6b85" + } +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.Vector2MaterialSlot", + "m_ObjectId": "7dbe167981d2452a8248b6d23432a518", + "m_Id": 0, + "m_DisplayName": "uvIndex", + "m_SlotType": 0, + "m_Hidden": false, + "m_ShaderOutputName": "uvIndex", + "m_StageCapability": 3, + "m_Value": { + "x": 0.0, + "y": 0.0 + }, + "m_DefaultValue": { + "x": 0.0, + "y": 0.0 + }, + "m_Labels": [ + "X", + "Y" + ] +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.CustomFunctionNode", + "m_ObjectId": "83aca69ecbd845e888867dea88a660f1", + "m_Group": { + "m_Id": "" + }, + "m_Name": "Custom Function", + "m_DrawState": { + "m_Expanded": true, + "m_Position": { + "serializedVersion": "2", + "x": -405.0, + "y": -144.0, + "width": 237.99998474121095, + "height": 494.0 + } + }, + "m_Slots": [ + { + "m_Id": "7dbe167981d2452a8248b6d23432a518" + }, + { + "m_Id": "3e7d4ea371804f5c9265e859f8e8e08b" + }, + { + "m_Id": "cb715a22dd514d2f9ec4045d78f7361b" + }, + { + "m_Id": "c24141b2554f431fbe3223c66bd8f0f0" + }, + { + "m_Id": "ee509cecfe5046ebb88dc4c3ae5e2fed" + }, + { + "m_Id": "f08b7a93deeb46548e0a57309906d22a" + }, + { + "m_Id": "5ae3156d60f846c68b9b446bc239bbea" + } + ], + "synonyms": [], + "m_Precision": 0, + "m_PreviewExpanded": true, + "m_CustomColors": { + "m_SerializableColors": [] + }, + "m_SourceType": 0, + "m_FunctionName": "VA1", + "m_FunctionSource": "a1250bb4cf9f61147bba30a99144d8f2", + "m_FunctionBody": "Enter function body here..." +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.Vector2MaterialSlot", + "m_ObjectId": "91fad60529a14d678005224cfbac1b50", + "m_Id": 0, + "m_DisplayName": "UV", + "m_SlotType": 1, + "m_Hidden": false, + "m_ShaderOutputName": "Out", + "m_StageCapability": 3, + "m_Value": { + "x": 0.0, + "y": 0.0 + }, + "m_DefaultValue": { + "x": 0.0, + "y": 0.0 + }, + "m_Labels": [ + "X", + "Y" + ] +} + +{ + "m_SGVersion": 1, + "m_Type": "UnityEditor.ShaderGraph.Internal.Vector1ShaderProperty", + "m_ObjectId": "967e0c2bcb6e48c2b85b82c6d4c734a4", + "m_Guid": { + "m_GuidSerialized": "26e53708-434a-4d58-b8b2-d8fb8005d644" + }, + "m_Name": "MaxFrames", + "m_DefaultReferenceName": "Vector1_967e0c2bcb6e48c2b85b82c6d4c734a4", + "m_OverrideReferenceName": "", + "m_GeneratePropertyBlock": true, + "m_Precision": 0, + "overrideHLSLDeclaration": false, + "hlslDeclarationOverride": 0, + "m_Hidden": false, + "m_Value": 0.0, + "m_FloatType": 0, + "m_RangeValues": { + "x": 0.0, + "y": 1.0 + } +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.SamplerStateShaderProperty", + "m_ObjectId": "975a04061f8d4786bce18d1574108732", + "m_Guid": { + "m_GuidSerialized": "374e9a5f-1ef4-43a2-9ff2-6108a1976ab0" + }, + "m_Name": "SamplerState", + "m_DefaultReferenceName": "", + "m_OverrideReferenceName": "SamplerState_Linear_Repeat", + "m_GeneratePropertyBlock": true, + "m_Precision": 0, + "overrideHLSLDeclaration": false, + "hlslDeclarationOverride": 0, + "m_Hidden": false, + "m_Value": { + "m_filter": 0, + "m_wrap": 0 + } +} + +{ + "m_SGVersion": 1, + "m_Type": "UnityEditor.ShaderGraph.Internal.Vector2ShaderProperty", + "m_ObjectId": "a09a6ce7e08545d99b5bda70586f4e79", + "m_Guid": { + "m_GuidSerialized": "96fb959c-8624-4642-9ac6-6b405b5a6dd4" + }, + "m_Name": "UV", + "m_DefaultReferenceName": "Vector2_a09a6ce7e08545d99b5bda70586f4e79", + "m_OverrideReferenceName": "", + "m_GeneratePropertyBlock": true, + "m_Precision": 0, + "overrideHLSLDeclaration": false, + "hlslDeclarationOverride": 0, + "m_Hidden": false, + "m_Value": { + "x": 0.0, + "y": 0.0, + "z": 0.0, + "w": 0.0 + } +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.Vector1MaterialSlot", + "m_ObjectId": "ad82a5146c4a46cc98b02a7e412b84b9", + "m_Id": 2, + "m_DisplayName": "Alpha", + "m_SlotType": 0, + "m_Hidden": false, + "m_ShaderOutputName": "Alpha", + "m_StageCapability": 3, + "m_Value": 0.0, + "m_DefaultValue": 0.0, + "m_Labels": [] +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.Vector1MaterialSlot", + "m_ObjectId": "b23754f8d4404c9cb59d3879708464ad", + "m_Id": 0, + "m_DisplayName": "MaxFrames", + "m_SlotType": 1, + "m_Hidden": false, + "m_ShaderOutputName": "Out", + "m_StageCapability": 3, + "m_Value": 0.0, + "m_DefaultValue": 0.0, + "m_Labels": [ + "X" + ] +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.Vector3MaterialSlot", + "m_ObjectId": "b89a68670a6642e19ae1063415132848", + "m_Id": 1, + "m_DisplayName": "Position", + "m_SlotType": 0, + "m_Hidden": false, + "m_ShaderOutputName": "Position", + "m_StageCapability": 3, + "m_Value": { + "x": 0.0, + "y": 0.0, + "z": 0.0 + }, + "m_DefaultValue": { + "x": 0.0, + "y": 0.0, + "z": 0.0 + }, + "m_Labels": [ + "X", + "Y", + "Z" + ] +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.PropertyNode", + "m_ObjectId": "bc36bc83631c44e0b48e951b444ba971", + "m_Group": { + "m_Id": "" + }, + "m_Name": "Property", + "m_DrawState": { + "m_Expanded": true, + "m_Position": { + "serializedVersion": "2", + "x": -576.0, + "y": -8.0, + "width": 136.0, + "height": 34.0 + } + }, + "m_Slots": [ + { + "m_Id": "b23754f8d4404c9cb59d3879708464ad" + } + ], + "synonyms": [], + "m_Precision": 0, + "m_PreviewExpanded": true, + "m_CustomColors": { + "m_SerializableColors": [] + }, + "m_Property": { + "m_Id": "967e0c2bcb6e48c2b85b82c6d4c734a4" + } +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.Vector1MaterialSlot", + "m_ObjectId": "c24141b2554f431fbe3223c66bd8f0f0", + "m_Id": 4, + "m_DisplayName": "time", + "m_SlotType": 0, + "m_Hidden": false, + "m_ShaderOutputName": "time", + "m_StageCapability": 3, + "m_Value": 0.0, + "m_DefaultValue": 0.0, + "m_Labels": [ + "X" + ] +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.Texture2DInputMaterialSlot", + "m_ObjectId": "cb715a22dd514d2f9ec4045d78f7361b", + "m_Id": 2, + "m_DisplayName": "positionMap", + "m_SlotType": 0, + "m_Hidden": false, + "m_ShaderOutputName": "positionMap", + "m_StageCapability": 3, + "m_Texture": { + "m_SerializedTexture": "{\"texture\":{\"instanceID\":0}}", + "m_Guid": "" + }, + "m_DefaultType": 0 +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.Vector1MaterialSlot", + "m_ObjectId": "ee509cecfe5046ebb88dc4c3ae5e2fed", + "m_Id": 6, + "m_DisplayName": "maxFrames", + "m_SlotType": 0, + "m_Hidden": false, + "m_ShaderOutputName": "maxFrames", + "m_StageCapability": 3, + "m_Value": 0.0, + "m_DefaultValue": 0.0, + "m_Labels": [ + "X" + ] +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.Vector3MaterialSlot", + "m_ObjectId": "f08b7a93deeb46548e0a57309906d22a", + "m_Id": 9, + "m_DisplayName": "position", + "m_SlotType": 1, + "m_Hidden": false, + "m_ShaderOutputName": "position", + "m_StageCapability": 3, + "m_Value": { + "x": 0.0, + "y": 0.0, + "z": 0.0 + }, + "m_DefaultValue": { + "x": 0.0, + "y": 0.0, + "z": 0.0 + }, + "m_Labels": [ + "X", + "Y", + "Z" + ] +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.PropertyNode", + "m_ObjectId": "f39a0ab1ea5d4129b8c210c762bed693", + "m_Group": { + "m_Id": "" + }, + "m_Name": "Property", + "m_DrawState": { + "m_Expanded": true, + "m_Position": { + "serializedVersion": "2", + "x": -606.0, + "y": -80.0, + "width": 155.0, + "height": 34.0 + } + }, + "m_Slots": [ + { + "m_Id": "4820d64a797d4948a129f455b98feed8" + } + ], + "synonyms": [], + "m_Precision": 0, + "m_PreviewExpanded": true, + "m_CustomColors": { + "m_SerializableColors": [] + }, + "m_Property": { + "m_Id": "975a04061f8d4786bce18d1574108732" + } +} + +{ + "m_SGVersion": 1, + "m_Type": "UnityEditor.ShaderGraph.Internal.Vector1ShaderProperty", + "m_ObjectId": "f9b649ed28584dca8a522f3fb582f350", + "m_Guid": { + "m_GuidSerialized": "07478aa4-3d18-4430-bf12-24688db601b8" + }, + "m_Name": "Time", + "m_DefaultReferenceName": "Vector1_f9b649ed28584dca8a522f3fb582f350", + "m_OverrideReferenceName": "", + "m_GeneratePropertyBlock": true, + "m_Precision": 0, + "overrideHLSLDeclaration": false, + "hlslDeclarationOverride": 0, + "m_Hidden": false, + "m_Value": 0.0, + "m_FloatType": 0, + "m_RangeValues": { + "x": 0.0, + "y": 1.0 + } +} + +{ + "m_SGVersion": 0, + "m_Type": "UnityEditor.ShaderGraph.Texture2DMaterialSlot", + "m_ObjectId": "ffcaa3e5c6a5468c92d6d08c301a6f59", + "m_Id": 0, + "m_DisplayName": "PositionMap", + "m_SlotType": 1, + "m_Hidden": false, + "m_ShaderOutputName": "Out", + "m_StageCapability": 3 +} + diff --git a/Runtime/Shaders/SubGraphs/VA1.shadersubgraph.meta b/Runtime/Shaders/SubGraphs/VA1.shadersubgraph.meta new file mode 100644 index 0000000..60a73e3 --- /dev/null +++ b/Runtime/Shaders/SubGraphs/VA1.shadersubgraph.meta @@ -0,0 +1,10 @@ +fileFormatVersion: 2 +guid: 1f0d283d8c3880947b6db8f287317cb6 +ScriptedImporter: + internalIDToNameTable: [] + externalObjects: {} + serializedVersion: 2 + userData: + assetBundleName: + assetBundleVariant: + script: {fileID: 11500000, guid: 60072b568d64c40a485e0fc55012dc9f, type: 3}