Mesh.GetBindposes
Declaration
public NativeArray<Matrix4x4> GetBindposes();Возвращаемое значение
NativeArray<Matrix4x4>
A NativeArray который ссылается на внутренние данные bind pose меша. Массив использует Allocator.None Сохраняет свою силу до тех пор, пока сетка не будет изменена или уничтожена.
Описание
Получает матрицы привязки, используемые в расчетах скининга.
Обеспечивает доступ к матрицам привязки сетки, которые определяют обратное преобразование каждой кости в начальной позе сетки.
Поза связывания на каждом индексе соответствует кости на том же индексе в SkinnedMeshRenderer.bones. Этот метод даёт прямой доступ к внутренним данным меша без создания копии.
using System.Collections.Generic; using UnityEngine; using Unity.Collections;
public class BindPoseProcessor : MonoBehaviour { // This example assumes the script is attached to a GameObject // with a SkinnedMeshRenderer component. [ContextMenu("Restore Bindpose")] void ProcessBindPoses() { var renderer = GetComponent<SkinnedMeshRenderer>(); if (renderer == null || renderer.sharedMesh == null) return; var bones = renderer.bones; // Get the bind poses from the mesh. This returns a NativeArray for direct, // allocation-free access to the data. NativeArray<Matrix4x4> bindPoses = renderer.sharedMesh.GetBindposes();
if (bones.Length != bindPoses.Length) return;
var bindposesDict = new Dictionary<Transform, Matrix4x4>(); for (int i = 0; i < bones.Length; ++i) { bindposesDict.Add(bones[i], bindPoses[i]); }
// Iterate over each bone to reset its transform to its original bind pose. foreach (var bone in bones) { var matrix = bindposesDict[bone]; var wMatrix = matrix.inverse;
var isRootBone = !bindposesDict.ContainsKey(bone.parent); if (!isRootBone) { if (bone.parent) { // To get the local matrix, multiply the bone's bindpose by the inverse of its parent's bindpose. matrix *= bindposesDict[bone.parent].inverse; } // Invert the resulting matrix to get the final local-to-parent transformation. matrix = matrix.inverse;
// Decompose the local matrix to extract and set the bone's local scale and position. bone.localScale = new Vector3( matrix.GetColumn(0).magnitude, matrix.GetColumn(1).magnitude, matrix.GetColumn(2).magnitude ); bone.localPosition = matrix.MultiplyPoint(Vector3.zero); } // Set the bone's world rotation from the inverse bindpose matrix. bone.rotation = wMatrix.rotation; } } }
Дополнительные ресурсы: ,Mesh.bindposes,, ,SkinnedMeshRenderer.bones,.
Declaration
public void GetBindposes(List<Matrix4x4> bindposes);Параметры
| Параметр | Описание |
|---|---|
| связывающие | Список для получения связывающих матриц. |
Описание
Получает матрицы привязки, используемые в расчетах скининга.
Обеспечивает доступ к матрицам позиций привязки сетки, которые определяют обратное преобразование каждой кости в начальной позиции сетки.
Позиция привязки в каждом индексе соответствует кости в том же индексе в SkinnedMeshRenderer.bones. Этот метод полезен для сценариев, в которых вы хотите повторно использовать один и тот же список для нескольких вызовов и не хотите выделять новый массив при каждом доступе.
using System.Collections.Generic; using UnityEngine;
public class BindPoseProcessor : MonoBehaviour { // A reusable list to store the bind poses, avoiding repeated memory allocations. private List<Matrix4x4> m_BindPoses = new List<Matrix4x4>();
// This example assumes the script is attached to a GameObject // with a SkinnedMeshRenderer component. [ContextMenu("Restore Bindpose")] void ProcessBindPoses() { var renderer = GetComponent<SkinnedMeshRenderer>(); if (renderer == null || renderer.sharedMesh == null) return;
var bones = renderer.bones; // Get the bind poses by populating the pre-existing list. This avoids // allocating a new list for every call. renderer.sharedMesh.GetBindposes(m_BindPoses);
if (bones.Length != m_BindPoses.Count) return;
var bindposesDict = new Dictionary<Transform, Matrix4x4>(); for (int i = 0; i < bones.Length; ++i) { bindposesDict.Add(bones[i], m_BindPoses[i]); }
// Iterate over each bone to reset its transform to its original bind pose. foreach (var bone in bones) { var matrix = bindposesDict[bone]; var wMatrix = matrix.inverse;
var isRootBone = !bindposesDict.ContainsKey(bone.parent); if (!isRootBone) { if (bone.parent) { // To get the local matrix, multiply the bone's bindpose by the inverse of its parent's bindpose. matrix *= bindposesDict[bone.parent].inverse; }
// Invert the resulting matrix to get the final local-to-parent transformation. matrix = matrix.inverse;
// Decompose the local matrix to extract and set the bone's local scale and position. bone.localScale = new Vector3( matrix.GetColumn(0).magnitude, matrix.GetColumn(1).magnitude, matrix.GetColumn(2).magnitude ); bone.localPosition = matrix.MultiplyPoint(Vector3.zero); } // Set the bone's world rotation from the inverse bindpose matrix. bone.rotation = wMatrix.rotation; } } }
Дополнительные ресурсы: ,Mesh.bindposes,, ,SkinnedMeshRenderer.bones,.