using System;
namespace GodotHostTest.AetherBind;
///
/// An object that allows communication through scopes (or inside the scope itself) by providing a couple getter/setter that can be injected in different scopes (or the same scope).
///
/// The type that's been passed through scopes.
///
///
public class ValueProvider
{
private IValueGetter? _getter;
private bool _isSet;
private T? _value;
public ValueProvider()
{
Setter = new SetterImplementation(this);
}
public IValueSetter Setter { get; }
public IValueGetter Getter
{
get
{
_getter ??= !_isSet
? throw new InvalidOperationException($"Value of type {typeof(T)} has not been set yet.")
: new GetterImplementation(_value!);
return _getter;
}
}
private class SetterImplementation(ValueProvider valueProvider) : IValueSetter
{
public void Set(T value)
{
if (valueProvider._isSet)
throw new InvalidOperationException($"A value (of type {typeof(T)}) cannot be set more than once.");
valueProvider._value = value;
valueProvider._isSet = true;
}
}
private class GetterImplementation(T value) : IValueGetter
{
public T Value => value;
}
}