public static IFlowConnector <T> Connector <T>(this IFlowSource <T> source, T @default = default) { var connector = new FlowConnector <T>(@default); connector.ConnectTo(source); return(connector); }
public static IFlowSource <T> FilterChanges <T>(this IFlowSource <T> source, IDisposer?disposer = null) { var filtered = new FlowVar <T>(source.Value, disposer); // FlowVar ignores assignments when new value is equal to old one (so - we filter the changes) source.AddSubscription(filtered, () => { filtered.Value = source.Value; }); return(filtered); }
/// <summary> /// Create a FlowCache. /// </summary> /// <param name="source">Source to cache.</param> /// <param name="disposer">Disposer in case T is IArc (required).</param> /// <exception cref="Exception"> /// Throws Exception in case T is IArc and no disposer is supplied /// or T is not IArc and disposer is supplied. /// </exception> public FlowCache(IFlowSource <T> source, IDisposer?disposer = null) { SubscribeTo(source); GetValue = () => { int lastChangeCount; lock (_lock) { if (_isCached) { (_cachedValue as IArc)?.Acquire(); return(_cachedValue); } lastChangeCount = _changeCount; } // Calc may be lock, so is not locked to allow OnChange fire on another thread var newValue = source.Value; lock (_lock) { // Can be changed during Calc() by OnChange method, we have to return the value even if the value will not be used as cached later if (lastChangeCount != _changeCount) { return(newValue); } // Dispose previous value is necessary, this can not be done in OnChange methods, since some object need to be disposed in the same thread (like OpenGL) (_cachedValue as IArc)?.Dispose(); _cachedValue = newValue; _isCached = true; (newValue as IArc)?.Acquire(); return(newValue); } }; if (Helpers.IsInheritedFrom <T, IArc>()) { if (disposer == null) { throw new Exception($"IArc type {typeof(T)} requires disposer"); } disposer.Add(() => { (_cachedValue as IArc)?.Dispose(); _cachedValue = default !;
public void ConnectTo(IFlowSource <T>?source) { lock (_lock) { if (Equals(_source, source)) { return; } _subscription?.Dispose(); _subscription = null; _source = source; if (_source != null) { _subscription = DisposableSubscribeTo(_source); } OnChange(); } }
public static IFlowPathBuilder <TNext> Path <T, TNext>(this IFlowSource <T> root, Func <T, TNext> transition) where TNext : class, IFlowChangeable { return(new FlowBuilderBuilder <IFlowSource <T> >(root).Path(transition)); }
public static Action Action <T1>(this IFlowSource <T1> source, object owner, Action <T1> action) { return(Flow.Action(owner, source, action)); }
public static IFlowSource <T> Func <T1, T>(this IFlowSource <T1> source, Func <T1, T> func) { return(Flow.Func(source, func)); }
public static Action Action <T1, T2, T3, T4, T5, T6, T7, T8>(object owner, IFlowSource <T1> source1, IFlowSource <T2> source2, IFlowSource <T3> source3, IFlowSource <T4> source4, IFlowSource <T5> source5, IFlowSource <T6> source6, IFlowSource <T7> source7, IFlowSource <T8> source8, Action <T1, T2, T3, T4, T5, T6, T7, T8> action) { return(new FlowAction(owner, () => action(source1.Value, source2.Value, source3.Value, source4.Value, source5.Value, source6.Value, source7.Value, source8.Value), source1, source2, source3, source4, source5, source6, source7, source8)); }
public static Action Action <T1, T2, T3, T4, T5>(object owner, IFlowSource <T1> source1, IFlowSource <T2> source2, IFlowSource <T3> source3, IFlowSource <T4> source4, IFlowSource <T5> source5, Action <T1, T2, T3, T4, T5> action) { return(new FlowAction(owner, () => action(source1.Value, source2.Value, source3.Value, source4.Value, source5.Value), source1, source2, source3, source4, source5)); }
public static Action Action <T1, T2, T3>(object owner, IFlowSource <T1> source1, IFlowSource <T2> source2, IFlowSource <T3> source3, Action <T1, T2, T3> action) { return(new FlowAction(owner, () => action(source1.Value, source2.Value, source3.Value), source1, source2, source3)); }
public static Action Action <T1>(object owner, IFlowSource <T1> source, Action <T1> action) { return(new FlowAction(owner, () => action(source.Value), source)); }
public static IFlowSource <T> Func <T1, T2, T3, T4, T5, T6, T7, T8, T>(IFlowSource <T1> source1, IFlowSource <T2> source2, IFlowSource <T3> source3, IFlowSource <T4> source4, IFlowSource <T5> source5, IFlowSource <T6> source6, IFlowSource <T7> source7, IFlowSource <T8> source8, Func <T1, T2, T3, T4, T5, T6, T7, T8, T> func) { return(new FlowFunc <T>(() => func(source1.Value, source2.Value, source3.Value, source4.Value, source5.Value, source6.Value, source7.Value, source8.Value), source1, source2, source3, source4, source5, source6, source7, source8)); }
public static IFlowSource <T> Func <T1, T2, T3, T4, T5, T>(IFlowSource <T1> source1, IFlowSource <T2> source2, IFlowSource <T3> source3, IFlowSource <T4> source4, IFlowSource <T5> source5, Func <T1, T2, T3, T4, T5, T> func) { return(new FlowFunc <T>(() => func(source1.Value, source2.Value, source3.Value, source4.Value, source5.Value), source1, source2, source3, source4, source5)); }
public static IFlowSource <T> Func <T1, T2, T3, T>(IFlowSource <T1> source1, IFlowSource <T2> source2, IFlowSource <T3> source3, Func <T1, T2, T3, T> func) { return(new FlowFunc <T>(() => func(source1.Value, source2.Value, source3.Value), source1, source2, source3)); }
public static IFlowSource <T> Func <T1, T>(IFlowSource <T1> source, Func <T1, T> func) { return(new FlowFunc <T>(() => func(source.Value), source)); }