diff --git a/Project/Assets/LunarConsole/Scripts/Actions/CVar.cs b/Project/Assets/LunarConsole/Scripts/Actions/CVar.cs
index 13c77a58..72ce6577 100644
--- a/Project/Assets/LunarConsole/Scripts/Actions/CVar.cs
+++ b/Project/Assets/LunarConsole/Scripts/Actions/CVar.cs
@@ -19,7 +19,8 @@
// limitations under the License.
//
-using System;
+using System;
+using System.CodeDom;
using System.Collections;
using System.Collections.Generic;
using System.Reflection;
@@ -39,17 +40,79 @@ public enum CVarType
String
}
- struct CValue
+ public class CValue
{
public string stringValue;
public int intValue;
public float floatValue;
+ public bool boolValue;
+
+ public CVarType Type { get; }
+
+ public CValue(CVarType type, string value)
+ {
+ Type = type;
+
+ stringValue = value;
+ floatValue = IsInt || IsFloat ? StringUtils.ParseFloat(value, 0.0f) : 0.0f;
+ intValue = IsInt || IsFloat ? (int) floatValue : 0;
+ }
+
+ public CValue(CVarType type, int value)
+ {
+ Type = type;
+
+ stringValue = StringUtils.ToString(value);
+ intValue = value;
+ floatValue = value;
+ }
+
+ public CValue(CVarType type, float value)
+ {
+ Type = type;
+
+ stringValue = StringUtils.ToString(value);
+ intValue = (int) value;
+ floatValue = value;
+ }
+
+
+ public CValue(CVarType type, bool value)
+ {
+ Type = type;
+
+ boolValue = value;
+ intValue = value ? 1 : 0;
+ floatValue = intValue;
+ stringValue = intValue.ToString();
+ }
public bool Equals(ref CValue other)
{
return other.intValue == intValue &&
other.floatValue == floatValue &&
- other.stringValue == stringValue;
+ other.stringValue == stringValue &&
+ other.boolValue == boolValue;
+ }
+
+ public bool IsInt
+ {
+ get { return Type == CVarType.Integer || Type == CVarType.Boolean; }
+ }
+
+ public bool IsString
+ {
+ get { return Type == CVarType.String; }
+ }
+
+ public bool IsFloat
+ {
+ get { return Type == CVarType.Float; }
+ }
+
+ public bool IsBool
+ {
+ get { return Type == CVarType.Boolean; }
}
}
@@ -73,7 +136,7 @@ public bool IsValid
}
public enum CFlags
- {
+ {
///
/// No flags (default value)
///
@@ -90,6 +153,115 @@ public enum CFlags
NoArchive = 1 << 2
}
+ public interface ICVarProxy
+ {
+ CValue Value { get; set; }
+ }
+
+ public class CVarProxy : ICVarProxy
+ {
+ private Func GetFunc { get; }
+ private Func SetFunc { get; }
+ private CValue _value;
+
+ public CVarProxy()
+ {
+ GetFunc = () =>
+ {
+ if (typeof(T) == typeof(int))
+ {
+ return (T) Convert.ChangeType(_value.intValue, typeof(T));
+ }
+
+ if (typeof(T) == typeof(float))
+ {
+ return (T) Convert.ChangeType(_value.floatValue, typeof(T));
+ }
+
+ if (typeof(T) == typeof(string))
+ {
+ return (T) Convert.ChangeType(_value.stringValue, typeof(T));
+ }
+
+ if (typeof(T) == typeof(bool))
+ {
+ return (T) Convert.ChangeType(_value.boolValue, typeof(T));
+ }
+
+ throw new ArgumentException();
+ };
+
+ SetFunc = value => value;
+ }
+
+ public CVarProxy(Func getFunc, Func setFunc)
+ {
+ GetFunc = getFunc;
+ SetFunc = setFunc;
+ }
+
+ public CValue Value
+ {
+ get
+ {
+ var value = GetFunc.Invoke();
+
+ if (typeof(T) == typeof(int))
+ {
+ _value = new CValue(CVarType.Integer, (int) Convert.ChangeType(value, typeof(int)));
+ }
+ else if (typeof(T) == typeof(float))
+ {
+ _value = new CValue(CVarType.Float, (float) Convert.ChangeType(value, typeof(float)));
+ }
+ else if (typeof(T) == typeof(string))
+ {
+ _value = new CValue(CVarType.String, (string) Convert.ChangeType(value, typeof(string)));
+ }
+ else if (typeof(T) == typeof(bool))
+ {
+ _value = new CValue(CVarType.Boolean, (bool) Convert.ChangeType(value, typeof(bool)));
+ }
+ else
+ {
+ throw new ArgumentException();
+ }
+
+ return _value;
+ }
+ set
+ {
+ _value = value;
+
+ if (typeof(T) == typeof(int))
+ {
+ SetFunc.Invoke((T) Convert.ChangeType(_value.intValue, typeof(T)));
+ return;
+ }
+
+ if (typeof(T) == typeof(float))
+ {
+ SetFunc.Invoke((T) Convert.ChangeType(_value.floatValue, typeof(T)));
+ return;
+ }
+
+ if (typeof(T) == typeof(string))
+ {
+ SetFunc.Invoke((T) Convert.ChangeType(_value.stringValue, typeof(T)));
+ return;
+ }
+
+ if (typeof(T) == typeof(bool))
+ {
+ SetFunc.Invoke((T) Convert.ChangeType(_value.boolValue, typeof(T)));
+ return;
+ }
+
+ throw new ArgumentException();
+ }
+ }
+ }
+
public class CVar : IEquatable, IComparable
{
private static int s_nextId;
@@ -99,38 +271,59 @@ public class CVar : IEquatable, IComparable
private readonly CVarType m_type;
private readonly CFlags m_flags;
- private CValue m_value;
private CValue m_defaultValue;
private CVarValueRange m_range = CVarValueRange.Undefined;
private CVarChangedDelegateList m_delegateList;
- public CVar(string name, bool defaultValue, CFlags flags = CFlags.None)
+ private CVarProxy m_intProxy;
+ private CVarProxy m_boolProxy;
+ private CVarProxy m_floatProxy;
+ private CVarProxy m_stringProxy;
+
+ private ICVarProxy Proxy
+ {
+ get
+ {
+ if (m_intProxy != null) return m_intProxy;
+ if (m_boolProxy != null) return m_boolProxy;
+ if (m_floatProxy != null) return m_floatProxy;
+ if (m_stringProxy != null) return m_stringProxy;
+
+ throw new ArgumentException();
+ }
+ }
+
+ public CVar(string name, bool defaultValue, CFlags flags = CFlags.None, CVarProxy proxy = null)
: this(name, CVarType.Boolean, flags)
{
- this.IntValue = defaultValue ? 1 : 0;
- m_defaultValue = m_value;
+ m_boolProxy = proxy ?? new CVarProxy();
+ BoolValue = defaultValue;
+ m_defaultValue = new CValue(m_type, defaultValue);
}
- public CVar(string name, int defaultValue, CFlags flags = CFlags.None)
+ public CVar(string name, int defaultValue, CFlags flags = CFlags.None, CVarProxy proxy = null)
: this(name, CVarType.Integer, flags)
{
- this.IntValue = defaultValue;
- m_defaultValue = m_value;
+ m_intProxy = proxy ?? new CVarProxy();
+ IntValue = defaultValue;
+ m_defaultValue = new CValue(m_type, defaultValue);
}
- public CVar(string name, float defaultValue, CFlags flags = CFlags.None)
+ public CVar(string name, float defaultValue, CFlags flags = CFlags.None, CVarProxy proxy = null)
: this(name, CVarType.Float, flags)
{
- this.FloatValue = defaultValue;
- m_defaultValue = m_value;
+ m_floatProxy = proxy ?? new CVarProxy();
+ FloatValue = defaultValue;
+ m_defaultValue = new CValue(m_type, defaultValue);
}
- public CVar(string name, string defaultValue, CFlags flags = CFlags.None)
+ public CVar(string name, string defaultValue, CFlags flags = CFlags.None, CVarProxy proxy = null)
: this(name, CVarType.String, flags)
{
- this.Value = defaultValue;
- m_defaultValue = m_value;
+ m_stringProxy = proxy ?? new CVarProxy();
+ Value = defaultValue;
+ m_defaultValue = new CValue(m_type, defaultValue);
}
private CVar(string name, CVarType type, CFlags flags)
@@ -219,7 +412,7 @@ public bool Equals(CVar other)
{
return other != null &&
other.m_name == m_name &&
- other.m_value.Equals(ref m_value) &&
+ other.Proxy.Value.Equals(Proxy.Value) &&
other.m_defaultValue.Equals(ref m_defaultValue) &&
other.m_type == m_type;
}
@@ -263,19 +456,17 @@ public string DefaultValue
public bool IsString
{
- get { return m_type == CVarType.String; }
+ get { return Proxy.Value.IsString; }
}
public string Value
{
- get { return m_value.stringValue; }
+ get { return Proxy.Value.stringValue; }
set
{
- bool changed = m_value.stringValue != value;
+ var changed = Proxy.Value.stringValue != value;
- m_value.stringValue = value;
- m_value.floatValue = IsInt || IsFloat ? StringUtils.ParseFloat(value, 0.0f) : 0.0f;
- m_value.intValue = IsInt || IsFloat ? (int)FloatValue : 0;
+ Proxy.Value = new CValue(m_type, value);
if (changed)
{
@@ -297,19 +488,17 @@ public bool HasRange
public bool IsInt
{
- get { return m_type == CVarType.Integer || m_type == CVarType.Boolean; }
+ get { return Proxy.Value.IsInt; }
}
public int IntValue
{
- get { return m_value.intValue; }
+ get => Proxy.Value.intValue;
set
{
- bool changed = m_value.intValue != value;
+ var changed = Proxy.Value.intValue != value;
- m_value.stringValue = StringUtils.ToString(value);
- m_value.intValue = value;
- m_value.floatValue = (float)value;
+ Proxy.Value = new CValue(m_type, value);
if (changed)
{
@@ -320,21 +509,19 @@ public int IntValue
public bool IsFloat
{
- get { return m_type == CVarType.Float; }
+ get { return Proxy.Value.Type == CVarType.Float; }
}
public float FloatValue
{
- get { return m_value.floatValue; }
+ get { return Proxy.Value.floatValue; }
set
{
- float oldValue = m_value.floatValue;
+ var changed = Proxy.Value.floatValue != value;
- m_value.stringValue = StringUtils.ToString(value);
- m_value.intValue = (int)value;
- m_value.floatValue = value;
+ Proxy.Value = new CValue(m_type, value);
- if (oldValue != value)
+ if (changed)
{
NotifyValueChanged();
}
@@ -343,22 +530,25 @@ public float FloatValue
public bool IsBool
{
- get { return m_type == CVarType.Boolean; }
+ get { return Proxy.Value.IsBool; }
}
public bool BoolValue
{
- get { return m_value.intValue != 0; }
- set { this.IntValue = value ? 1 : 0; }
+ get { return Proxy.Value.intValue != 0; }
+ set
+ {
+ Proxy.Value = new CValue(m_type, value);
+ }
}
public bool IsDefault
{
- get { return m_value.Equals(m_defaultValue); }
+ get { return Proxy.Value.Equals(m_defaultValue); }
set
{
- bool changed = this.IsDefault ^ value;
- m_value = m_defaultValue;
+ bool changed = IsDefault ^ value;
+ Proxy.Value = m_defaultValue;
if (changed)
{
@@ -383,22 +573,22 @@ public CFlags Flags
public static implicit operator string(CVar cvar)
{
- return cvar.m_value.stringValue;
+ return cvar.Proxy.Value.stringValue;
}
public static implicit operator int(CVar cvar)
{
- return cvar.m_value.intValue;
+ return cvar.Proxy.Value.intValue;
}
public static implicit operator float(CVar cvar)
{
- return cvar.m_value.floatValue;
+ return cvar.Proxy.Value.floatValue;
}
public static implicit operator bool(CVar cvar)
{
- return cvar.m_value.intValue != 0;
+ return cvar.Proxy.Value.intValue != 0;
}
#endregion
@@ -470,7 +660,7 @@ public IEnumerator GetEnumerator()
#region IEnumerable implementation
- System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()
+ IEnumerator IEnumerable.GetEnumerator()
{
return m_variables.GetEnumerator();
}
@@ -483,7 +673,7 @@ public int Count
}
}
- [AttributeUsage (AttributeTargets.Field, Inherited = true, AllowMultiple = false)]
+ [AttributeUsage (AttributeTargets.Field)]
public sealed class CVarRangeAttribute : Attribute
{
public readonly float min;
@@ -538,4 +728,4 @@ static void NullCVarChangedDelegate(CVar cvar)
{
}
}
-}
\ No newline at end of file
+}