Merge pull request #1803 from Santarh/controlRigOptions

Replace control rig generation option with enum in vrm 1.0
This commit is contained in:
ousttrue 2022-09-21 16:33:24 +09:00 committed by GitHub
commit ea660c68dc
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
13 changed files with 71 additions and 42 deletions

View File

@ -61,7 +61,7 @@ namespace UniVRM10
bool m_done;
async Task SetupSelfRendererAsync(GameObject go, UniGLTF.RuntimeGltfInstance runtime,
Transform FirstPersonBone, RendererFirstPersonFlags x,
Transform firstPersonBone, RendererFirstPersonFlags x,
(int FirstPersonOnly, int ThirdPersonOnly) layer, IAwaitCaller awaitCaller = null)
{
switch (x.FirstPersonFlag)
@ -70,7 +70,7 @@ namespace UniVRM10
{
if (x.GetRenderer(go.transform) is SkinnedMeshRenderer smr)
{
var eraseBones = GetBonesThatHasAncestor(smr, FirstPersonBone);
var eraseBones = GetBonesThatHasAncestor(smr, firstPersonBone);
if (eraseBones.Any())
{
// オリジナルのモデルを3人称用にする
@ -92,7 +92,7 @@ namespace UniVRM10
}
else if (x.GetRenderer(go.transform) is MeshRenderer mr)
{
if (mr.transform.Ancestors().Any(y => y == FirstPersonBone))
if (mr.transform.Ancestors().Any(y => y == firstPersonBone))
{
// 頭の子孫なので1人称では非表示に
mr.gameObject.layer = layer.ThirdPersonOnly;
@ -154,7 +154,9 @@ namespace UniVRM10
m_done = true;
var runtime = go.GetComponent<UniGLTF.RuntimeGltfInstance>();
var firstPersonBone = go.GetComponent<Animator>().GetBoneTransform(HumanBodyBones.Head);
var vrmInstance = go.GetComponent<Vrm10Instance>();
// NOTE: This bone must be referenced by renderers instead of the control rig bone.
var firstPersonBone = vrmInstance.Humanoid.Head;
var used = new HashSet<string>();
foreach (var x in Renderers)

View File

@ -5,9 +5,9 @@ namespace UniVRM10
{
/// <summary>
/// VRM全体を制御するRoot
///
///
/// Importer(scripted importer) -> Prefab(editor/asset) -> Instance(scene/MonoBehavior) -> Runtime(play時)
///
///
/// * DefaultExecutionOrder(11000) means calculate springbone after FinalIK( VRIK )
/// </summary>
[AddComponentMenu("VRM10/VRMInstance")]
@ -52,8 +52,12 @@ namespace UniVRM10
private UniHumanoid.Humanoid m_humanoid;
private Vrm10Runtime m_runtime;
private bool m_generateControlRig = false;
private ControlRigGenerationOption m_controlRigGenerationOption = ControlRigGenerationOption.None;
/// <summary>
/// VRM ファイルに記録された Humanoid ボーンに対応します。
/// これは、コントロールリグのボーンとは異なります。
/// </summary>
public UniHumanoid.Humanoid Humanoid
{
get
@ -75,15 +79,15 @@ namespace UniVRM10
{
if (m_runtime == null)
{
m_runtime = new Vrm10Runtime(this, m_generateControlRig);
m_runtime = new Vrm10Runtime(this, m_controlRigGenerationOption);
}
return m_runtime;
}
}
internal void InitializeAtRuntime(bool generateControlRig)
internal void InitializeAtRuntime(ControlRigGenerationOption controlRigGenerationOption)
{
m_generateControlRig = generateControlRig;
m_controlRigGenerationOption = controlRigGenerationOption;
}
void Start()

View File

@ -0,0 +1,16 @@
namespace UniVRM10
{
public enum ControlRigGenerationOption
{
/// <summary>
/// コントロールリグを生成しません。
/// </summary>
None,
/// <summary>
/// 推奨されるオプションです。
/// コントロールリグのボーン Transform を生成し、Root の Animator はコントロールリグのボーンを制御するようになります。
/// </summary>
Generate,
}
}

View File

@ -0,0 +1,3 @@
fileFormatVersion: 2
guid: 9723f89e671a460188d12cbcceccaa4e
timeCreated: 1663314138

View File

@ -58,7 +58,8 @@ namespace UniVRM10
BoneType = boneType;
ControlTarget = controlTarget;
ControlBone = new GameObject(boneType.ToString()).transform;
// NOTE: bone name must be unique in the vrm instance.
ControlBone = new GameObject($"{nameof(Vrm10ControlBone)}:{boneType.ToString()}").transform;
ControlBone.position = controlTarget.position;
InitialControlBoneLocalPosition = ControlBone.localPosition;
InitialControlBoneLocalRotation = ControlBone.localRotation;

View File

@ -38,7 +38,7 @@ namespace UniVRM10
public Vrm10RuntimeExpression Expression { get; }
public Vrm10RuntimeLookAt LookAt { get; }
public Vrm10Runtime(Vrm10Instance target, bool generateControlRig)
public Vrm10Runtime(Vrm10Instance target, ControlRigGenerationOption controlRigGenerationOption)
{
m_target = target;
@ -47,9 +47,9 @@ namespace UniVRM10
throw new Exception();
}
if (generateControlRig)
if (controlRigGenerationOption != ControlRigGenerationOption.None)
{
ControlRig = new Vrm10RuntimeControlRig(target.Humanoid, m_target.transform);
ControlRig = new Vrm10RuntimeControlRig(target.Humanoid, m_target.transform, controlRigGenerationOption);
}
Constraints = target.GetComponentsInChildren<IVrm10Constraint>();
LookAt = new Vrm10RuntimeLookAt(target.Vrm.LookAt, target.Humanoid, m_head, target.LookAtTargetType, target.Gaze);

View File

@ -28,8 +28,10 @@ namespace UniVRM10
/// コンストラクタ。
/// humanoid は VRM T-Pose でなければならない。
/// </summary>
public Vrm10RuntimeControlRig(UniHumanoid.Humanoid humanoid, Transform vrmRoot)
public Vrm10RuntimeControlRig(UniHumanoid.Humanoid humanoid, Transform vrmRoot, ControlRigGenerationOption option)
{
if (option == ControlRigGenerationOption.None) return;
_controlRigRoot = new GameObject("Runtime Control Rig").transform;
_controlRigRoot.SetParent(vrmRoot);
@ -39,9 +41,10 @@ namespace UniVRM10
InitialHipsHeight = _hipBone.ControlTarget.position.y;
var transformBonePairs = _bones.Select(kv => (kv.Value.ControlBone, kv.Key));
_controlRigAvatar = HumanoidLoader.LoadHumanoidAvatar(_controlRigRoot, transformBonePairs);
_controlRigAvatar = HumanoidLoader.LoadHumanoidAvatar(vrmRoot, transformBonePairs);
_controlRigAvatar.name = "Runtime Control Rig";
ControlRigAnimator = _controlRigRoot.gameObject.AddComponent<Animator>();
ControlRigAnimator = vrmRoot.GetComponent<Animator>();
ControlRigAnimator.avatar = _controlRigAvatar;
}

View File

@ -27,7 +27,7 @@ namespace UniVRM10
/// </summary>
/// <param name="path">vrm file path</param>
/// <param name="canLoadVrm0X">if true, this loader can load the vrm-0.x model as vrm-1.0 model with migration.</param>
/// <param name="generateControlRig">if true, generating the control rig provides bone manipulation like vrm-0.x</param>
/// <param name="controlRigGenerationOption">the flag of generating the control rig provides bone manipulation unified between models.</param>
/// <param name="showMeshes">if true, show meshes when loaded.</param>
/// <param name="awaitCaller">this loader use specified await strategy.</param>
/// <param name="materialGenerator">this loader use specified material generation strategy.</param>
@ -37,7 +37,7 @@ namespace UniVRM10
public static async Task<Vrm10Instance> LoadPathAsync(
string path,
bool canLoadVrm0X = true,
bool generateControlRig = true,
ControlRigGenerationOption controlRigGenerationOption = ControlRigGenerationOption.Generate,
bool showMeshes = true,
IAwaitCaller awaitCaller = null,
IMaterialDescriptorGenerator materialGenerator = null,
@ -55,7 +55,7 @@ namespace UniVRM10
path,
System.IO.File.ReadAllBytes(path),
canLoadVrm0X,
generateControlRig,
controlRigGenerationOption,
showMeshes,
awaitCaller,
materialGenerator,
@ -71,7 +71,7 @@ namespace UniVRM10
/// </summary>
/// <param name="bytes">vrm file data</param>
/// <param name="canLoadVrm0X">if true, this loader can load the vrm-0.x model as vrm-1.0 model with migration.</param>
/// <param name="generateControlRig">if true, generating the control rig provides bone manipulation like vrm-0.x</param>
/// <param name="controlRigGenerationOption">the flag of generating the control rig provides bone manipulation unified between models.</param>
/// <param name="showMeshes">if true, show meshes when loaded.</param>
/// <param name="awaitCaller">this loader use specified await strategy.</param>
/// <param name="materialGenerator">this loader use specified material generation strategy.</param>
@ -81,7 +81,7 @@ namespace UniVRM10
public static async Task<Vrm10Instance> LoadBytesAsync(
byte[] bytes,
bool canLoadVrm0X = true,
bool generateControlRig = true,
ControlRigGenerationOption controlRigGenerationOption = ControlRigGenerationOption.Generate,
bool showMeshes = true,
IAwaitCaller awaitCaller = null,
IMaterialDescriptorGenerator materialGenerator = null,
@ -99,7 +99,7 @@ namespace UniVRM10
string.Empty,
bytes,
canLoadVrm0X,
generateControlRig,
controlRigGenerationOption,
showMeshes,
awaitCaller,
materialGenerator,
@ -111,7 +111,7 @@ namespace UniVRM10
string name,
byte[] bytes,
bool canLoadVrm0X,
bool generateControlRig,
ControlRigGenerationOption controlRigGenerationOption,
bool showMeshes,
IAwaitCaller awaitCaller,
IMaterialDescriptorGenerator materialGenerator,
@ -129,7 +129,7 @@ namespace UniVRM10
// 1. Try loading as vrm-1.0
var instance = await TryLoadingAsVrm10Async(
gltfData,
generateControlRig,
controlRigGenerationOption,
showMeshes,
awaitCaller,
materialGenerator,
@ -154,7 +154,7 @@ namespace UniVRM10
// 3. Try migration from vrm-0.x into vrm-1.0
var migratedInstance = await TryMigratingFromVrm0XAsync(
gltfData,
generateControlRig,
controlRigGenerationOption,
showMeshes,
awaitCaller,
materialGenerator,
@ -177,7 +177,7 @@ namespace UniVRM10
private static async Task<Vrm10Instance> TryLoadingAsVrm10Async(
GltfData gltfData,
bool generateControlRig,
ControlRigGenerationOption controlRigGenerationOption,
bool showMeshes,
IAwaitCaller awaitCaller,
IMaterialDescriptorGenerator materialGenerator,
@ -202,7 +202,7 @@ namespace UniVRM10
return await LoadVrm10DataAsync(
vrm10Data,
null,
generateControlRig,
controlRigGenerationOption,
showMeshes,
awaitCaller,
materialGenerator,
@ -212,7 +212,7 @@ namespace UniVRM10
private static async Task<Vrm10Instance> TryMigratingFromVrm0XAsync(
GltfData gltfData,
bool generateControlRig,
ControlRigGenerationOption controlRigGenerationOption,
bool showMeshes,
IAwaitCaller awaitCaller,
IMaterialDescriptorGenerator materialGenerator,
@ -239,7 +239,7 @@ namespace UniVRM10
var migratedVrm10Instance = await LoadVrm10DataAsync(
migratedVrm10Data,
migrationData,
generateControlRig,
controlRigGenerationOption,
showMeshes,
awaitCaller,
materialGenerator,
@ -256,7 +256,7 @@ namespace UniVRM10
private static async Task<Vrm10Instance> LoadVrm10DataAsync(
Vrm10Data vrm10Data,
MigrationData migrationData,
bool generateControlRig,
ControlRigGenerationOption controlRigGenerationOption,
bool showMeshes,
IAwaitCaller awaitCaller,
IMaterialDescriptorGenerator materialGenerator,
@ -274,7 +274,7 @@ namespace UniVRM10
throw new ArgumentNullException(nameof(vrm10Data));
}
using (var loader = new Vrm10Importer(vrm10Data, generateControlRig: generateControlRig, materialGenerator: materialGenerator))
using (var loader = new Vrm10Importer(vrm10Data, controlRigGenerationOption: controlRigGenerationOption, materialGenerator: materialGenerator))
{
// 1. Load meta information if callback was available.
if (vrmMetaInformationCallback != null)

View File

@ -18,7 +18,7 @@ namespace UniVRM10
private readonly Vrm10Data m_vrm;
/// VrmLib.Model の オブジェクトと UnityEngine.Object のマッピングを記録する
private readonly ModelMap m_map = new ModelMap();
private readonly bool m_generateControlRig;
private readonly ControlRigGenerationOption m_controlRigGenerationOption;
private VrmLib.Model m_model;
private IReadOnlyDictionary<SubAssetKey, UnityEngine.Object> m_externalMap;
@ -31,7 +31,7 @@ namespace UniVRM10
IReadOnlyDictionary<SubAssetKey, UnityEngine.Object> externalObjectMap = null,
ITextureDeserializer textureDeserializer = null,
IMaterialDescriptorGenerator materialGenerator = null,
bool generateControlRig = false)
ControlRigGenerationOption controlRigGenerationOption = ControlRigGenerationOption.None)
: base(vrm.Data, externalObjectMap, textureDeserializer)
{
if (vrm == null)
@ -39,7 +39,7 @@ namespace UniVRM10
throw new ArgumentNullException("vrm");
}
m_vrm = vrm;
m_generateControlRig = generateControlRig;
m_controlRigGenerationOption = controlRigGenerationOption;
TextureDescriptorGenerator = new Vrm10TextureDescriptorGenerator(Data);
MaterialDescriptorGenerator = materialGenerator ?? new Vrm10MaterialDescriptorGenerator();
@ -246,7 +246,7 @@ namespace UniVRM10
// VrmController
var controller = Root.AddComponent<Vrm10Instance>();
controller.InitializeAtRuntime(m_generateControlRig);
controller.InitializeAtRuntime(m_controlRigGenerationOption);
controller.enabled = false;
// vrm

View File

@ -22,12 +22,12 @@ namespace UniVRM10.Sample
async void Run()
{
var src = new FileInfo(m_vrmPath);
var instance = await Vrm10.LoadPathAsync(m_vrmPath, true, true);
var instance = await Vrm10.LoadPathAsync(m_vrmPath, true);
var exportedBytes = Vrm10Exporter.Export(instance.gameObject);
// Import 1.0
var vrm10 = await Vrm10.LoadBytesAsync(exportedBytes, false, true);
var vrm10 = await Vrm10.LoadBytesAsync(exportedBytes, false);
var pos = vrm10.transform.position;
pos.x += 1.5f;
vrm10.transform.position = pos;

View File

@ -32,7 +32,7 @@ namespace UniVRM10.Test
controller.Vrm.Expression.Aa.MaterialColorBindings = src.ToArray();
// ok if no exception
var r = new Vrm10Runtime(controller, false);
var r = new Vrm10Runtime(controller, ControlRigGenerationOption.None);
}
[Test]
@ -56,7 +56,7 @@ namespace UniVRM10.Test
controller.Vrm.Expression.Aa.MaterialUVBindings = src.ToArray();
// ok if no exception
var r = new Vrm10Runtime(controller, false);
var r = new Vrm10Runtime(controller, ControlRigGenerationOption.None);
}
}
}

View File

@ -198,7 +198,7 @@ namespace UniVRM10
{
try
{
Vrm10.LoadPathAsync(gltf.FullName, true, false).Wait();
Vrm10.LoadPathAsync(gltf.FullName, true, ControlRigGenerationOption.None).Wait();
}
catch (UnNormalizedException)
{

View File

@ -16,7 +16,7 @@ namespace UniVRM10
public static Vrm10Instance LoadAlicia()
{
var task = Vrm10.LoadPathAsync(AliciaPath, true, true);
var task = Vrm10.LoadPathAsync(AliciaPath, canLoadVrm0X: true);
task.Wait();
var instance = task.Result;