Meaning... if someone changes the color property of a script in the Inspector at runtime, is there a way to detect that event?
you can "detect" it by saving the value constantly and compare it with its actual value like
color oldColor;
color newColor;
update()
{
newColor = object.color;
if(oldColor!= newColor)
{
Debug.log("The color change was realized");
}
oldColor = object.color;
}
thats one way to see the change, hope this helps you
This actually isn’t a valid solution due to floating point precision issues (trust me, I’ve been at this for a full day now). I’m working on a method that will compare a specific precision of the float
for each rgba channel in two colors, but I’m trying to make it quick enough that the compare isn’t detrimental when run in Update()
.
I’ve also seen a recommendation to use inverselerp
, but that seems costly in Update()
or FixedUpdate()
This is what I just coded up that works really well and simple to use:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using System.Text;
using System.Threading.Tasks;
public class PropertyNotifier<T>
{
object Instance;
FieldInfo Field;
MethodInfo OnChangedMethod;
public PropertyNotifier(object propertyObject, string fieldName)
{
// verify object
Instance = propertyObject;
// pull field for the property on the object
Field = Instance.GetType().GetField(fieldName);
if (Field == null)
throw new Exception(Instance.GetType().Name + "." + fieldName + " not found!");
// pull changed method for the property on the object
var changedMethodName = "On" + fieldName + "Changed";
OnChangedMethod = Instance.GetType().GetMethod(changedMethodName, BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);
if (OnChangedMethod == null)
throw new Exception(Instance.GetType().Name + "." + changedMethodName + " not found. Please create it!");
}
public void Set(T value)
{
T currentValue = (T)Field.GetValue(Instance);
if (currentValue == null && value == null)
return;
if (currentValue != null && value != null && currentValue.Equals(value))
return;
Field.SetValue(Instance, value);
OnChangedMethod.Invoke(Instance, null);
}
public void ForceNotification()
{
OnChangedMethod.Invoke(Instance, null);
}
}
public class TestClass
{
public int IntField;
PropertyNotifier<int> IntProperty;
public string StrField;
PropertyNotifier<string> StrProperty;
public TestClass()
{
IntProperty = new PropertyNotifier<int>(this, "IntField");
StrProperty = new PropertyNotifier<string>(this, "StrField");
IntProperty.Set(5);
IntProperty.Set(6);
IntProperty.Set(6);
IntProperty.Set(7);
StrProperty.Set(null);
StrProperty.Set("hello");
StrProperty.Set("hello");
StrProperty.Set("world");
StrProperty.Set(null);
}
void OnIntFieldChanged()
{
System.Diagnostics.Debug.WriteLine("OnIntMemberChanged to " + IntField);
}
void OnStrFieldChanged()
{
System.Diagnostics.Debug.WriteLine("OnStrMemberChanged to " + (string.IsNullOrEmpty(StrField) ? "nullOrEmpty" : StrField));
}
}
It produces the following output:
OnIntMemberChanged to 5
OnIntMemberChanged to 6
OnIntMemberChanged to 7
OnStrMemberChanged to hello
OnStrMemberChanged to world
OnStrMemberChanged to nullOrEmpty