using System; using System.Collections.Generic; using System.Reflection; using Golems.Attributes; namespace Golems { public partial class AttributesEditor { const BindingFlags k_OnValChangedFlags = BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic; private Dictionary m_Fields = new Dictionary(); private void OnInspectorGUIOnValueChangedAttribute() { var targetType = target.GetType(); var fields = targetType.GetFields(k_OnValChangedFlags); // // Search for OnValueChanged Attribute on Each Field on this Object // for (int i = 0, counti = fields.Length; i < counti; ++i) { var field = fields[i]; var onValueChangedAttribute = field.GetCustomAttribute(); // // If we find an attribute and haven't already included it in m_Fields, include it! // if (onValueChangedAttribute == null || m_Fields.TryGetValue(field.Name, out var fieldValue)) continue; var method = targetType.GetMethod(onValueChangedAttribute.Method, k_ButtonBindingFlags); if (method != null) { m_Fields.Add(field.Name, field.GetValue(this.target)); } } var changed = new List(); // // Now check all our found Fields and see if a value has changed // foreach (var fieldValueKeypair in m_Fields) { // // Retrieve the FieldInfo for the cached field name // var fieldInfo = targetType.GetField(fieldValueKeypair.Key, k_OnValChangedFlags); if (fieldInfo == null) continue; // // Detect any change? // var currentValue = fieldInfo.GetValue(target); if (currentValue != null && currentValue.Equals(fieldValueKeypair.Value) || currentValue == null && fieldValueKeypair.Value == null) continue; var key = fieldValueKeypair.Key; changed.Add(() => { m_Fields[key] = currentValue; }); // ...a bit lazy, probably should cache this stuff but here we are :( var onValueChangedAttribute = fieldInfo.GetCustomAttribute(); if (onValueChangedAttribute == null) continue; var method = targetType.GetMethod(onValueChangedAttribute.Method, k_ButtonBindingFlags); method?.Invoke(target, null); } // // Update m_Fields which have been changed // changed.ForEach(x => x.Invoke()); } } }