Initial commit almost identical to SVN-repo rev.340
This commit is contained in:
@@ -0,0 +1,199 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
using log4net;
|
||||
|
||||
namespace TBF.BenchControl
|
||||
{
|
||||
public class State
|
||||
{
|
||||
/// <summary>
|
||||
/// DEBUG: all state changes and all operations
|
||||
/// INFO: all state changes and operations that returned evnt != Event.None
|
||||
/// WARN: only state changes
|
||||
/// </summary>
|
||||
private static readonly ILog log = LogManager.GetLogger(typeof(State));
|
||||
public override string ToString() { return Name + (Label==null ? "" : ", label=" + Label); }
|
||||
|
||||
/// <summary>Current state (static)</summary>
|
||||
public static State CurrentState
|
||||
{
|
||||
get { return currentState; }
|
||||
}
|
||||
static State currentState;
|
||||
|
||||
/// <summary>State with an empty list of operations</summary>
|
||||
/// <remarks>Useful when entering the first state and leaving the last one</remarks>
|
||||
public static State Empty
|
||||
{
|
||||
get { return new State("empty"); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Static constructor that initializes CurrentState
|
||||
/// </summary>
|
||||
static State()
|
||||
{
|
||||
currentState = State.Empty;
|
||||
}
|
||||
|
||||
///
|
||||
/// Instance fields set or initialized by the constructor
|
||||
///
|
||||
public readonly IList<IOperation> Operations;
|
||||
public readonly IList<Transition> Transitions;
|
||||
public readonly string Name;
|
||||
public readonly string Label;
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Constructor with a label
|
||||
/// </summary>
|
||||
public State(string name, string label)
|
||||
{
|
||||
this.Name = name;
|
||||
this.Label = label;
|
||||
Operations = new List<IOperation>();
|
||||
Transitions = new List<Transition>();
|
||||
log.Debug(this.ToString());
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Default constructor
|
||||
/// </summary>
|
||||
public State(string name)
|
||||
: this(name, null)
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Create a new state without a label
|
||||
/// </summary>
|
||||
public static State Create(string name)
|
||||
{
|
||||
return new State(name);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Create a new state with a label
|
||||
/// </summary>
|
||||
public static State Create(string name, string label)
|
||||
{
|
||||
return new State(name, label);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add an operation to this state
|
||||
/// </summary>
|
||||
/// <param name="obj">operation</param>
|
||||
public State AddOperation(IOperation operation)
|
||||
{
|
||||
if (operation != null) Operations.Add(operation);
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add a list of operations to this state
|
||||
/// </summary>
|
||||
/// <param name="obj">operation</param>
|
||||
public State AddOperations(IList<IOperation> operations)
|
||||
{
|
||||
if (operations != null)
|
||||
{
|
||||
foreach (var op in operations) { if (op != null) Operations.Add(op); }
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add a state transition to the state
|
||||
/// </summary>
|
||||
/// <param name="obj">transition</param>
|
||||
public State AddTransition(Transition transition)
|
||||
{
|
||||
if (transition != null) Transitions.Add(transition);
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Enter a new state
|
||||
/// </summary>
|
||||
public State EnterState()
|
||||
{
|
||||
ChangeState(State.currentState, this);
|
||||
State.currentState = this;
|
||||
UiBridge.Bridge.OnStateChanged(this, State.currentState.ToString());
|
||||
return this;
|
||||
}
|
||||
|
||||
// ----------------------------------- Run time -----------------------------------------
|
||||
|
||||
/// <summary>
|
||||
/// Execute Run() methods of all operations of the current state.
|
||||
/// </summary>
|
||||
/// <returns>List of Event-s returned from the state operations</returns>
|
||||
public static IList<Event> RunOperations()
|
||||
{
|
||||
IList<Event> events = new List<Event>();
|
||||
|
||||
foreach (IOperation operation in currentState.Operations)
|
||||
{
|
||||
Event evnt = operation.Run();
|
||||
if (evnt != Event.None)
|
||||
{
|
||||
log.InfoFormat("Operation {0} returned {1}", operation, evnt);
|
||||
events.Add(evnt);
|
||||
}
|
||||
else
|
||||
{
|
||||
log.DebugFormat("Operation {0} returned {1}", operation, evnt);
|
||||
}
|
||||
}
|
||||
|
||||
return events;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Execute Stop() methods of all operations of the current state.
|
||||
/// </summary>
|
||||
public static void StopOperations()
|
||||
{
|
||||
foreach (IOperation operation in currentState.Operations)
|
||||
{
|
||||
log.DebugFormat("stopping {0}", operation);
|
||||
operation.Stop();
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Run Stop() and Start() methods of operations when changing the state.
|
||||
/// </summary>
|
||||
/// <param name="previousState">Stopping state</param>
|
||||
/// <param name="newState">Starting state</param>
|
||||
static void ChangeState(State previousState, State newState)
|
||||
{
|
||||
/// Stop() the previous state operations, which are not in the next state
|
||||
foreach (IOperation operation in previousState.Operations)
|
||||
{
|
||||
if (!newState.Operations.Contains(operation))
|
||||
{
|
||||
log.DebugFormat("stopping {0}", operation);
|
||||
operation.Stop();
|
||||
}
|
||||
}
|
||||
|
||||
log.WarnFormat("ChangeState( {0} -> {1} )", previousState.ToString(), newState.ToString());
|
||||
|
||||
/// Start() the operations that are in the current (new) state, but aren't in the previous state.
|
||||
foreach (IOperation operation in newState.Operations)
|
||||
{
|
||||
if (!previousState.Operations.Contains(operation))
|
||||
{
|
||||
log.DebugFormat("starting {0}", operation);
|
||||
operation.Start();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user