您最多选择25个主题 主题必须以中文或者字母或数字开头,可以包含连字符 (-),并且长度不得超过35个字符

221 行
7.6 KiB

namespace UniVRM10
{
public static class VRM10SpringUtility
{
#if false
#if UNITY_EDITOR
#region save
[MenuItem(VRMVersion.MENU + "/SaveSpringBoneToJSON", validate = true)]
static bool SaveSpringBoneToJSONIsEnable()
{
var root = Selection.activeObject as GameObject;
if (root == null)
{
return false;
}
var animator = root.GetComponent<Animator>();
if (animator == null)
{
return false;
}
return true;
}
[MenuItem(VRMVersion.MENU + "/SaveSpringBoneToJSON")]
static void SaveSpringBoneToJSON()
{
var path = EditorUtility.SaveFilePanel(
"Save spring to json",
null,
"VRMSpring.json",
"json");
if (string.IsNullOrEmpty(path))
{
return;
}
var go = Selection.activeObject as GameObject;
var root = go.transform;
var nodes = root.Traverse().Skip(1).ToList();
var spring = new glTF_VRM_SecondaryAnimation();
ExportSecondary(root, nodes,
spring.colliderGroups.Add,
spring.boneGroups.Add
);
File.WriteAllText(path, spring.ToJson());
}
#endregion
#region load
[MenuItem(VRMVersion.MENU + "/LoadSpringBoneFromJSON", true)]
static bool LoadSpringBoneFromJSONIsEnable()
{
var root = Selection.activeObject as GameObject;
if (root == null)
{
return false;
}
var animator = root.GetComponent<Animator>();
if (animator == null)
{
return false;
}
return true;
}
[MenuItem(VRMVersion.MENU + "/LoadSpringBoneFromJSON")]
static void LoadSpringBoneFromJSON()
{
var path = EditorUtility.OpenFilePanel(
"Load spring from json",
null,
"json");
if (string.IsNullOrEmpty(path))
{
return;
}
var json = File.ReadAllText(path, Encoding.UTF8);
var spring = JsonUtility.FromJson<glTF_VRM_SecondaryAnimation>(json);
var go = Selection.activeObject as GameObject;
var root = go.transform;
var nodes = root.Traverse().Skip(1).ToList();
LoadSecondary(root, nodes, spring);
}
#endregion
#endif
public static void ExportSecondary(Transform root, List<Transform> nodes,
Action<glTF_VRM_SecondaryAnimationColliderGroup> addSecondaryColliderGroup,
Action<glTF_VRM_SecondaryAnimationGroup> addSecondaryGroup)
{
var colliders = new List<VRMSpringBoneColliderGroup>();
foreach (var vrmColliderGroup in root.Traverse()
.Select(x => x.GetComponent<VRMSpringBoneColliderGroup>())
.Where(x => x != null))
{
colliders.Add(vrmColliderGroup);
var colliderGroup = new glTF_VRM_SecondaryAnimationColliderGroup
{
node = nodes.IndexOf(vrmColliderGroup.transform)
};
colliderGroup.colliders = vrmColliderGroup.Colliders.Select(x =>
{
return new glTF_VRM_SecondaryAnimationCollider
{
offset = x.Offset,
radius = x.Radius,
};
}).ToList();
addSecondaryColliderGroup(colliderGroup);
}
foreach (var spring in root.Traverse()
.SelectMany(x => x.GetComponents<VRMSpringBone>())
.Where(x => x != null))
{
addSecondaryGroup(new glTF_VRM_SecondaryAnimationGroup
{
comment = spring.m_comment,
center = nodes.IndexOf(spring.m_center),
dragForce = spring.m_dragForce,
gravityDir = spring.m_gravityDir,
gravityPower = spring.m_gravityPower,
stiffiness = spring.m_stiffnessForce,
hitRadius = spring.m_hitRadius,
colliderGroups = spring.ColliderGroups
.Select(x => colliders.IndexOf(x))
.Where(x => x != -1)
.ToArray(),
bones = spring.RootBones.Select(x => nodes.IndexOf(x)).ToArray(),
});
}
}
public static void LoadSecondary(Transform root, List<Transform> nodes,
glTF_VRM_SecondaryAnimation secondaryAnimation)
{
var secondary = root.Find("secondary");
if (secondary == null)
{
secondary = new GameObject("secondary").transform;
secondary.SetParent(root, false);
}
// clear components
var remove = root.Traverse()
.SelectMany(x => x.GetComponents<Component>())
.Where(x => x is VRMSpringBone || x is VRMSpringBoneColliderGroup)
.ToArray();
foreach (var x in remove)
{
if (Application.isPlaying)
{
GameObject.Destroy(x);
}
else
{
GameObject.DestroyImmediate(x);
}
}
//var secondaryAnimation = context.VRM.extensions.VRM.secondaryAnimation;
var colliders = new List<VRMSpringBoneColliderGroup>();
foreach (var colliderGroup in secondaryAnimation.colliderGroups)
{
var vrmGroup = nodes[colliderGroup.node].gameObject.AddComponent<VRMSpringBoneColliderGroup>();
vrmGroup.Colliders = colliderGroup.colliders.Select(x =>
{
return new VRMSpringBoneColliderGroup.SphereCollider
{
Offset = x.offset,
Radius = x.radius
};
}).ToArray();
colliders.Add(vrmGroup);
}
if (secondaryAnimation.boneGroups.Count > 0)
{
foreach (var boneGroup in secondaryAnimation.boneGroups)
{
var vrmBoneGroup = secondary.gameObject.AddComponent<VRMSpringBone>();
if (boneGroup.center != -1)
{
vrmBoneGroup.m_center = nodes[boneGroup.center];
}
vrmBoneGroup.m_comment = boneGroup.comment;
vrmBoneGroup.m_dragForce = boneGroup.dragForce;
vrmBoneGroup.m_gravityDir = boneGroup.gravityDir;
vrmBoneGroup.m_gravityPower = boneGroup.gravityPower;
vrmBoneGroup.m_hitRadius = boneGroup.hitRadius;
vrmBoneGroup.m_stiffnessForce = boneGroup.stiffiness;
if (boneGroup.colliderGroups != null && boneGroup.colliderGroups.Any())
{
vrmBoneGroup.ColliderGroups = boneGroup.colliderGroups.Select(x => colliders[x]).ToArray();
}
vrmBoneGroup.RootBones = boneGroup.bones.Select(x => nodes[x]).ToList();
}
}
else
{
secondary.gameObject.AddComponent<VRMSpringBone>();
}
}
#endif
}
}