using System.Collections.Generic;
using System.Linq;
using UnityEngine;
using VrmLib;
namespace UniVRM10
{
///
/// ブレンドシェイプを蓄えてまとめて適用するクラス
///
internal sealed class ExpressionMerger
{
///
/// Key から Expression を得る
///
Dictionary m_clipMap;
///
/// Expression のWeightを記録する
///
Dictionary m_valueMap;
MorphTargetBindingMerger m_morphTargetBindingMerger;
MaterialValueBindingMerger m_materialValueBindingMerger;
public ExpressionMerger(VRM10ObjectExpression expressions, Transform root)
{
m_clipMap = expressions.Clips.ToDictionary(x => expressions.CreateKey(x.Clip), x => x.Clip);
m_valueMap = new Dictionary();
m_morphTargetBindingMerger = new MorphTargetBindingMerger(m_clipMap, root);
m_materialValueBindingMerger = new MaterialValueBindingMerger(m_clipMap, root);
}
///
/// まとめて反映する。1フレームに1回呼び出されることを想定
///
///
public void SetValues(Dictionary expressionWeights)
{
foreach (var (key, weight) in expressionWeights.Select(kv => (kv.Key, kv.Value)))
{
AccumulateValue(key, weight);
}
m_morphTargetBindingMerger.Apply();
m_materialValueBindingMerger.Apply();
}
private void AccumulateValue(ExpressionKey key, float value)
{
m_valueMap[key] = value;
VRM10Expression clip;
if (!m_clipMap.TryGetValue(key, out clip))
{
return;
}
m_morphTargetBindingMerger.AccumulateValue(clip, value);
m_materialValueBindingMerger.AccumulateValue(clip, value);
}
public void RestoreMaterialInitialValues()
{
m_materialValueBindingMerger.RestoreMaterialInitialValues();
}
}
}