Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
【Unity】Animatorのステートを自動取得してモーションを確認できるUIパネル(Editor only)
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
#if UNITY_EDITOR
using UnityEditor.Animations;
#endif
/// <summary>
/// Mecanimモーション確認用のUIパネル
/// </summary>
public class MecanimCheckPanel : MonoBehaviour
{
/// <summary>
/// ターゲットのアニメーター
/// </summary>
[SerializeField]
private Animator _animator = null;
/// <summary>
/// レイヤー切り替えドロップダウン
/// </summary>
[SerializeField]
private Dropdown _layerDropdown = null;
/// <summary>
/// ステート切り替えドロップダウン
/// </summary>
[SerializeField]
private Dropdown _stateDropdown = null;
/// <summary>
/// モーション移行時間
/// </summary>
[SerializeField]
private float _crossFadeDuration = 0.2f;
private Dictionary<string, List<string>> _layerStatesTable = new Dictionary<string, List<string>>();
private void Awake()
{
#if UNITY_EDITOR
// AnimatorControllerのデータ収集
var layerNameList = new List<string>();
var controller = _animator.runtimeAnimatorController as AnimatorController;
foreach (var layer in controller.layers)
{
layerNameList.Add(layer.name);
var stateNameList = new List<string>();
foreach (var child in layer.stateMachine.states)
{
stateNameList.Add(child.state.name);
}
_layerStatesTable.Add(layer.name, stateNameList);
}
// Dropdownの設定
_layerDropdown.ClearOptions();
_stateDropdown.ClearOptions();
_layerDropdown.AddOptions(layerNameList);
_layerDropdown.onValueChanged.AddListener(x => RefreshStateDropdown(_layerDropdown.options[x].text));
_stateDropdown.onValueChanged.AddListener(x =>
{
ChangeMotion(_layerDropdown.options[_layerDropdown.value].text, _stateDropdown.options[x].text);
});
#else
// Editor only
Destroy(gameObject);
#endif
}
private void Start()
{
_layerDropdown.onValueChanged.Invoke(0);
}
/// <summary>
/// ステートのドロップダウンを更新
/// </summary>
/// <param name="layer">レイヤー名</param>
private void RefreshStateDropdown(string layer)
{
_stateDropdown.ClearOptions();
_stateDropdown.AddOptions(_layerStatesTable[layer]);
_stateDropdown.onValueChanged.Invoke(0);
}
/// <summary>
/// モーションを変更する
/// </summary>
/// <param name="layerName">レイヤー名</param>
/// <param name="stateName">目標ステート名</param>
private void ChangeMotion(string layerName, string stateName)
{
var layer = _animator.GetLayerIndex(layerName);
_animator.CrossFadeInFixedTime(stateName, _crossFadeDuration, layer);
}
}
@neuneu9
Copy link
Author

neuneu9 commented Nov 5, 2020

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment