Skip to content

Commit

Permalink
fix: add bones, if bones are not set (#310)
Browse files Browse the repository at this point in the history
<!-- Copy the TICKETID for this task from Jira and add it to the PR name
in brackets -->
<!-- PR name should look like: [TICKETID] My Pull Request -->

<!-- Add link for the ticket here editing the TICKETID-->

## [TICKETID](https://ready-player-me.atlassian.net/browse/TICKETID)

## Description

-   Briefly describe what this change will do

<!-- Fill the section below with Added, Updated and Removed information.
-->
<!-- If there is no item under one of the lists remove it's title. -->

<!-- Testability -->

## How to Test

-   Add steps to locally test these changes

<!-- Update your progress with the task here -->

## Checklist

-   [ ] Tests written or updated for the changes.
-   [ ] Documentation is updated.
-   [ ] Changelog is updated.

<!--- Remember to copy the Changes Section into the commit message when
you close the PR -->
  • Loading branch information
rk132 authored Jul 15, 2024
2 parents 4611b5a + 4607cc0 commit 9d0ee93
Showing 1 changed file with 20 additions and 12 deletions.
32 changes: 20 additions & 12 deletions Runtime/Core/Scripts/Utils/AvatarMeshHelper.cs
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,8 @@ namespace ReadyPlayerMe.Core
{
public static class AvatarMeshHelper
{
private static readonly string[] headMeshNames = {
private static readonly string[] headMeshNames =
{
"Renderer_Head",
"Renderer_Hair",
"Renderer_Beard",
Expand All @@ -16,15 +17,15 @@ public static class AvatarMeshHelper
"Renderer_EyeLeft",
"Renderer_EyeRight",
"Renderer_Headwear",
"Renderer_Facewear",
"Renderer_Facewear"
};

[Obsolete("Use TransferMesh(GameObject source, GameObject target) instead.")]
public static void TransferMesh(GameObject source, SkinnedMeshRenderer[] targetMeshes, Animator targetAnimator)
{
TransferMesh(source, targetMeshes[0].transform.parent.gameObject);
}

/// <summary>
/// Transfers the mesh and material data from the source to the target avatar.
/// </summary>
Expand All @@ -34,23 +35,30 @@ public static void TransferMesh(GameObject source, GameObject target)
{
// store the relevant data of the source (downloaded) avatar
var rendererDict = new Dictionary<string, SkinnedMeshRenderer>();

var sourceRenderers = source.GetComponentsInChildren<SkinnedMeshRenderer>();
var targetRenderers = target.GetComponentsInChildren<SkinnedMeshRenderer>();

foreach (var renderer in sourceRenderers)
{
rendererDict.Add(renderer.name, renderer);
}


var meshWithBones = targetRenderers.DefaultIfEmpty(null).FirstOrDefault((renderer) => renderer.bones.Length != 0);

// transfer the data to the target skinning mesh renderers
foreach (var renderer in targetRenderers)
{
if (rendererDict.TryGetValue(renderer.name, out var sourceRenderer))
{
renderer.sharedMesh = sourceRenderer.sharedMesh;
renderer.sharedMaterial = sourceRenderer.sharedMaterial;


if (renderer.bones.Length == 0 && meshWithBones != null)
{
renderer.bones = meshWithBones.bones;
continue;
}
// transfer the bone data
foreach (var targetBone in renderer.bones)
{
Expand All @@ -61,7 +69,7 @@ public static void TransferMesh(GameObject source, GameObject target)
targetBone.position = sourceBone.position;
targetBone.rotation = sourceBone.rotation;
targetBone.localScale = sourceBone.localScale;
break;
break;
}
}
}
Expand All @@ -72,13 +80,13 @@ public static void TransferMesh(GameObject source, GameObject target)
renderer.material = null;
}
}

// transfer the animation avatar
var sourceAnimator = source.GetComponentInChildren<Animator>();
var targetAnimator = target.GetComponentInChildren<Animator>();
targetAnimator.avatar = sourceAnimator.avatar;
}

/// <summary>
/// Returns the meshes of the head of the avatar, such as glasses, hair, teeth, etc.
/// </summary>
Expand All @@ -88,15 +96,15 @@ public static GameObject[] GetHeadMeshes(GameObject avatar)
{
var renderers = avatar.GetComponentsInChildren<SkinnedMeshRenderer>();
var headMeshes = new List<GameObject>();

foreach (var renderer in renderers)
{
if (headMeshNames.Contains(renderer.name))
{
headMeshes.Add(renderer.gameObject);
}
}

return headMeshes.ToArray();
}
}
Expand Down

0 comments on commit 9d0ee93

Please sign in to comment.