Heroes_of_Hiis/Assets/Oculus/Avatar/Scripts/OvrAvatarRenderComponent.cs

136 lines
5.2 KiB
C#

using UnityEngine;
using System.Collections;
using System.Collections.Generic;
using System;
using Oculus.Avatar;
public class OvrAvatarRenderComponent : MonoBehaviour {
private bool firstSkinnedUpdate = true;
public SkinnedMeshRenderer mesh;
public Transform[] bones;
bool isBodyComponent = false;
protected void UpdateActive(OvrAvatar avatar, ovrAvatarVisibilityFlags mask)
{
bool doActiveHack = isBodyComponent && avatar.EnableExpressive && avatar.ShowFirstPerson && !avatar.ShowThirdPerson;
if (doActiveHack)
{
bool showFirstPerson = (mask & ovrAvatarVisibilityFlags.FirstPerson) != 0;
bool showThirdPerson = (mask & ovrAvatarVisibilityFlags.ThirdPerson) != 0;
gameObject.SetActive(showThirdPerson || showThirdPerson);
if (!showFirstPerson)
{
mesh.enabled = false;
}
}
else
{
bool active = avatar.ShowFirstPerson && (mask & ovrAvatarVisibilityFlags.FirstPerson) != 0;
active |= avatar.ShowThirdPerson && (mask & ovrAvatarVisibilityFlags.ThirdPerson) != 0;
this.gameObject.SetActive(active);
mesh.enabled = active;
}
}
protected SkinnedMeshRenderer CreateSkinnedMesh(ulong assetID, ovrAvatarVisibilityFlags visibilityMask, int thirdPersonLayer, int firstPersonLayer)
{
isBodyComponent = name.Contains("body");
OvrAvatarAssetMesh meshAsset = (OvrAvatarAssetMesh)OvrAvatarSDKManager.Instance.GetAsset(assetID);
if (meshAsset == null)
{
throw new Exception("Couldn't find mesh for asset " + assetID);
}
if ((visibilityMask & ovrAvatarVisibilityFlags.ThirdPerson) != 0)
{
this.gameObject.layer = thirdPersonLayer;
}
else
{
this.gameObject.layer = firstPersonLayer;
}
SkinnedMeshRenderer renderer = meshAsset.CreateSkinnedMeshRendererOnObject(gameObject);
#if UNITY_ANDROID
renderer.quality = SkinQuality.Bone2;
#else
renderer.quality = SkinQuality.Bone4;
#endif
renderer.updateWhenOffscreen = true;
if ((visibilityMask & ovrAvatarVisibilityFlags.SelfOccluding) == 0)
{
renderer.shadowCastingMode = UnityEngine.Rendering.ShadowCastingMode.Off;
}
gameObject.SetActive(false);
return renderer;
}
protected void UpdateSkinnedMesh(OvrAvatar avatar, Transform[] bones, ovrAvatarTransform localTransform, ovrAvatarVisibilityFlags visibilityMask, IntPtr renderPart)
{
UpdateActive(avatar, visibilityMask);
OvrAvatar.ConvertTransform(localTransform, this.transform);
ovrAvatarRenderPartType type = CAPI.ovrAvatarRenderPart_GetType(renderPart);
UInt64 dirtyJoints;
switch (type)
{
case ovrAvatarRenderPartType.SkinnedMeshRender:
dirtyJoints = CAPI.ovrAvatarSkinnedMeshRender_GetDirtyJoints(renderPart);
break;
case ovrAvatarRenderPartType.SkinnedMeshRenderPBS:
dirtyJoints = CAPI.ovrAvatarSkinnedMeshRenderPBS_GetDirtyJoints(renderPart);
break;
case ovrAvatarRenderPartType.SkinnedMeshRenderPBS_V2:
dirtyJoints = CAPI.ovrAvatarSkinnedMeshRenderPBSV2_GetDirtyJoints(renderPart);
break;
default:
throw new Exception("Unhandled render part type: " + type);
}
for (UInt32 i = 0; i < 64; i++)
{
UInt64 dirtyMask = (ulong)1 << (int)i;
// We need to make sure that we fully update the initial position of
// Skinned mesh renderers, then, thereafter, we can only update dirty joints
if ((firstSkinnedUpdate && i < bones.Length) ||
(dirtyMask & dirtyJoints) != 0)
{
//This joint is dirty and needs to be updated
Transform targetBone = bones[i];
ovrAvatarTransform transform;
switch (type)
{
case ovrAvatarRenderPartType.SkinnedMeshRender:
transform = CAPI.ovrAvatarSkinnedMeshRender_GetJointTransform(renderPart, i);
break;
case ovrAvatarRenderPartType.SkinnedMeshRenderPBS:
transform = CAPI.ovrAvatarSkinnedMeshRenderPBS_GetJointTransform(renderPart, i);
break;
case ovrAvatarRenderPartType.SkinnedMeshRenderPBS_V2:
transform = CAPI.ovrAvatarSkinnedMeshRenderPBSV2_GetJointTransform(renderPart, i);
break;
default:
throw new Exception("Unhandled render part type: " + type);
}
OvrAvatar.ConvertTransform(transform, targetBone);
}
}
firstSkinnedUpdate = false;
}
protected Material CreateAvatarMaterial(string name, Shader shader)
{
if (shader == null)
{
throw new Exception("No shader provided for avatar material.");
}
Material mat = new Material(shader);
mat.name = name;
return mat;
}
}