Skip to content

Commit

Permalink
Change StateMachine.NET.
Browse files Browse the repository at this point in the history
  - Remove Context::ThreadType enum.
  - Add AsyncContext class which inherits from Context.
  • Loading branch information
cozzyy2002 committed Jan 11, 2020
1 parent 36e7fd0 commit 73782c1
Show file tree
Hide file tree
Showing 6 changed files with 69 additions and 57 deletions.
3 changes: 1 addition & 2 deletions StateMachine.NET.TestConsole/Program.cs
Original file line number Diff line number Diff line change
Expand Up @@ -40,9 +40,8 @@ static void Main(string[] args)
}
}

class Context : tsm_NET.Generic.Context<Event, State>
class Context : tsm_NET.Generic.AsyncContext<Event, State>
{
public Context() : base(ThreadType.Native) { }
}

class State : tsm_NET.Generic.State<Context, Event, State>
Expand Down
54 changes: 36 additions & 18 deletions StateMachine.NET.UnitTest/Class1.cs
Original file line number Diff line number Diff line change
Expand Up @@ -6,27 +6,25 @@

namespace StateMachine.NET.UnitTest.Generic
{
public class Context : Context<Event, State>
[TestFixture]
public class TestCase
{
public Context() { }
public Context(ThreadType threadType) : base(threadType) { }
}
public class Context : Context<Event, State>
{
}

public class Event : Event<Context>
{
public static Event Null { get; } = null;
}
public class Event : Event<Context>
{
public static Event Null { get; } = null;
}

public class State : State<Context, Event, State>
{
public static State Null { get; } = null;
}
public class State : State<Context, Event, State>
{
public static State Null { get; } = null;
}

[TestFixture]
public class GenericTestCase
{
[Test]
public void SyncContextTest()
public void BasicTest()
{
var mockEvent = Substitute.For<Event>();
var mockInitialState = Substitute.For<State>();
Expand Down Expand Up @@ -88,16 +86,36 @@ public void SyncContextTest()
mockStateMonitor.DidNotReceive().onIdle(Arg.Any<Context>());
mockStateMonitor.DidNotReceive().onWorkerThreadExit(Arg.Any<Context>(), Arg.Any<HResult>());
}
}

[TestFixture]
public class AsyncTestCase
{
public class Context : AsyncContext<Event, State>
{
// StateMachine should run on managed thread to test on NUnit.
public Context() : base(true) { }
}

public class Event : Event<Context>
{
public static Event Null { get; } = null;
}

public class State : State<Context, Event, State>
{
public static State Null { get; } = null;
}

[Test]
public void BasicTest()
{
var mockEvent = Substitute.For<Event>();
var mockEvent = Substitute.For<Event>();
var mockInitialState = Substitute.For<State>();
var mockNextState = Substitute.For<State>();
var mockStateMonitor = Substitute.For<IStateMonitor<Event, State>>();

var c = new Context(Context.ThreadType.Managed);
var c = new Context();
c.StateMonitor = mockStateMonitor;
Assert.That(c.CurrentState, Is.EqualTo(null), "Context has no initial state when created.");

Expand Down
5 changes: 3 additions & 2 deletions StateMachine.NET.UnitTest/Class2.cs
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
namespace StateMachine.NET.UnitTest
{
[TestFixture]
public class TestCase
public class AsyncTestCase
{
[Test]
public void BasicTest()
Expand All @@ -17,7 +17,8 @@ public void BasicTest()
var mockNextState = Substitute.For<State>();
var mockStateMonitor = Substitute.For<IStateMonitor>();

var c = new Context(Context.ThreadType.Managed);
// StateMachine should run on managed thread to test on NUnit.
var c = new AsyncContext(true);
c.StateMonitor = mockStateMonitor;
Assert.That(c.CurrentState, Is.EqualTo(null), "Context has no initial state when created.");

Expand Down
14 changes: 12 additions & 2 deletions StateMachine.NET/GenericObject.h
Original file line number Diff line number Diff line change
Expand Up @@ -43,9 +43,11 @@ public ref class StateMonitorCaller : public tsm_NET::StateMonitorCaller
generic<typename E, typename S>
public ref class Context : public tsm_NET::Context
{
protected:
Context(bool isAsync, bool useNativeThread) : tsm_NET::Context(isAsync, useNativeThread), m_stateMonitor(nullptr) {}

public:
Context() : tsm_NET::Context(), m_stateMonitor(nullptr) {}
Context(ThreadType threadType) : tsm_NET::Context(threadType), m_stateMonitor(nullptr) {}
Context() : tsm_NET::Context(false, false), m_stateMonitor(nullptr) {}
virtual ~Context() {}

HResult setup(S initialState, E event) { return (HResult)tsm_NET::Context::setup((tsm_NET::State^)initialState, (tsm_NET::Event^)event); }
Expand All @@ -72,6 +74,14 @@ public ref class Context : public tsm_NET::Context
StateMonitorCaller<E, S>^ m_stateMonitorCaller;
};

generic<typename E, typename S>
public ref class AsyncContext : public Context<E, S>
{
public:
AsyncContext() : Context(true, false) {}
AsyncContext(bool useNativeThread) : Context(true, useNativeThread) {}
};

generic<typename C, typename E, typename S>
where C : tsm_NET::Context
where E : tsm_NET::Event
Expand Down
22 changes: 3 additions & 19 deletions StateMachine.NET/StateMachine.NET.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -60,25 +60,9 @@ void StateMonitorCaller::onWorkerThreadExitCallback(tsm::IContext* context, HRES
}

//-------------- Managed Context class. --------------------//
void Context::construct(ThreadType threadType)
{
bool isAsync;
switch(threadType) {
case ThreadType::None:
default:
isAsync = false;
m_useNativeThread = false;
break;
case ThreadType::Native:
isAsync = true;
m_useNativeThread = false;
break;
case ThreadType::Managed:
isAsync = true;
m_useNativeThread = true;
break;
}

void Context::construct(bool isAsync, bool useNativeThread)
{
m_useNativeThread = useNativeThread;
m_nativeContext = new native::Context(this, isAsync);
}

Expand Down
28 changes: 14 additions & 14 deletions StateMachine.NET/StateMachine.NET.h
Original file line number Diff line number Diff line change
Expand Up @@ -83,22 +83,13 @@ public ref class StateMonitorCaller

public ref class Context
{
public:
// Worker thread type on which StateMachine runs.
enum class ThreadType
{
// Description Thread creation StateMachine class
None, // No worker thread. None tsm::StateMachine
Native, // Use native thread. CreateThread() Win32 API tsm::AsyncStateMachine
Managed, // Use managed thiread System::Threading::Thread tsm::AsyncStateMachine
};
void construct(bool isAsync, bool useNativeThread);

private:
void construct(ThreadType threadType);
protected:
Context(bool isAsync, bool useNativeThread) { construct(isAsync, useNativeThread); }

public:
Context() { construct(ThreadType::None); }
Context(ThreadType threadType) { construct(threadType); }
Context() { construct(false, false); }
virtual ~Context();
!Context();

Expand Down Expand Up @@ -131,8 +122,17 @@ public ref class Context
protected:
NativeType* m_nativeContext;
bool m_useNativeThread;
tsm_NET::IStateMonitor^ m_stateMonitor;
StateMonitorCaller^ m_stateMonitorCaller;
tsm_NET::IStateMonitor^ m_stateMonitor;
};

public ref class AsyncContext : public Context
{
public:
AsyncContext() : Context(true, false) {}
AsyncContext(bool useNativeThread) : Context(true, useNativeThread) {}

protected:
};

public ref class State
Expand Down

0 comments on commit 73782c1

Please sign in to comment.