x) Add whatFile for fast cached lookup of filenames from a path x) Debug renames x) Add default OnChanged handler that does nothing x) Cleanups to the FSM stuff
100 lines
2.1 KiB
C#
100 lines
2.1 KiB
C#
|
|
|
|
using System;
|
|
using System.Runtime.CompilerServices;
|
|
using Optional;
|
|
|
|
|
|
|
|
namespace imm;
|
|
|
|
|
|
|
|
public record class Context : imm.Recorded<Context>
|
|
{
|
|
|
|
}
|
|
|
|
public record class State<TSUB, CTX>( CTX Context ) : imm.Recorded<TSUB>
|
|
where TSUB : State<TSUB, CTX>
|
|
where CTX : Context
|
|
{
|
|
virtual public (CTX, TSUB) onEnter(CTX ctx, State<TSUB, CTX> oldState)
|
|
{
|
|
return (ctx, (TSUB)this);
|
|
}
|
|
|
|
virtual public (CTX, TSUB) onExit(CTX ctx, State<TSUB, CTX> newState)
|
|
{
|
|
return (ctx, (TSUB)this);
|
|
}
|
|
}
|
|
|
|
|
|
|
|
public record class FSM<TSUB, ST, CTX> : imm.Recorded<TSUB>
|
|
where TSUB : FSM<TSUB, ST, CTX>
|
|
where ST : State<ST, CTX>
|
|
where CTX : Context
|
|
{
|
|
public CTX Context { get; init; }
|
|
public ST State { get; init; }
|
|
|
|
public FSM( CTX context, ST stStart )
|
|
{
|
|
Context = context;
|
|
State = stStart;
|
|
}
|
|
|
|
public TSUB Transition(ST newState, string reason,
|
|
[CallerMemberName] string memberName = "",
|
|
[CallerFilePath] string filePath = "",
|
|
[CallerLineNumber] int lineNumber = 0,
|
|
[CallerArgumentExpression("fn")]
|
|
string expression = default
|
|
)
|
|
{
|
|
log.debug( $"Trans from {State.GetType().Name} to {newState.GetType().Name} for {reason}" );
|
|
|
|
var origState = State;
|
|
|
|
var (newCtx, oldState) = State.onExit(Context, newState);
|
|
|
|
var (newCTX, storeState) = newState.onEnter(newCtx, oldState);
|
|
|
|
var newFSM = this.Process( (v) => (this as TSUB) with
|
|
{
|
|
Context = newCTX,
|
|
State = storeState,
|
|
}, $"{reason}" );
|
|
|
|
return newFSM;
|
|
}
|
|
|
|
/*
|
|
public TSUB ( Func<ST, ST> fn, string reason,
|
|
[CallerMemberName] string member = "",
|
|
[CallerFilePath] string file = "",
|
|
[CallerLineNumber] int line = 0,
|
|
[CallerArgumentExpression("fn")]
|
|
string expression = default
|
|
)
|
|
{
|
|
var newState = fn( State );
|
|
|
|
if( object.ReferenceEquals( newState, State ) ) return (TSUB)this;
|
|
|
|
TSUB newFSM = this.Process( this with
|
|
{
|
|
Context = Context,
|
|
State = newState,
|
|
}, $"Processing: {newState.GetType().Name} for {reason}",
|
|
member, file, line, expression );
|
|
|
|
return (TSUB)newFSM;
|
|
}
|
|
*/
|
|
|
|
}
|
|
|