feat: add shared runtime and codegen support
This commit is contained in:
@@ -0,0 +1,80 @@
|
||||
#nullable enable
|
||||
|
||||
using System;
|
||||
using System.Threading;
|
||||
using ShrinkSDK.Runtime;
|
||||
|
||||
namespace ShrinkEventBus
|
||||
{
|
||||
public static class ShrinkEventBusRuntime
|
||||
{
|
||||
private static IShrinkMainThreadDispatcher _mainThreadDispatcher = CreateDefaultDispatcher();
|
||||
|
||||
public static IShrinkMainThreadDispatcher MainThreadDispatcher =>
|
||||
Volatile.Read(ref _mainThreadDispatcher);
|
||||
|
||||
public static void ConfigureMainThreadDispatcher(IShrinkMainThreadDispatcher dispatcher)
|
||||
{
|
||||
if (dispatcher == null)
|
||||
throw new ArgumentNullException(nameof(dispatcher));
|
||||
Volatile.Write(ref _mainThreadDispatcher, dispatcher);
|
||||
}
|
||||
|
||||
private static IShrinkMainThreadDispatcher CreateDefaultDispatcher()
|
||||
{
|
||||
#if UNITY_5_3_OR_NEWER
|
||||
return new ShrinkUnityMainThreadDispatcher();
|
||||
#else
|
||||
return new ShrinkSynchronizationContextDispatcher(
|
||||
SynchronizationContext.Current,
|
||||
Thread.CurrentThread.ManagedThreadId);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
#if UNITY_5_3_OR_NEWER
|
||||
internal sealed class ShrinkUnityMainThreadDispatcher : IShrinkMainThreadDispatcher
|
||||
{
|
||||
public bool IsMainThread => Cysharp.Threading.Tasks.PlayerLoopHelper.IsMainThread;
|
||||
|
||||
public bool TryPost(Action action)
|
||||
{
|
||||
if (action == null)
|
||||
throw new ArgumentNullException(nameof(action));
|
||||
Cysharp.Threading.Tasks.PlayerLoopHelper.AddContinuation(
|
||||
Cysharp.Threading.Tasks.PlayerLoopTiming.Update,
|
||||
action);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
#else
|
||||
internal sealed class ShrinkSynchronizationContextDispatcher : IShrinkMainThreadDispatcher
|
||||
{
|
||||
private readonly SynchronizationContext? _context;
|
||||
private readonly int _threadId;
|
||||
|
||||
public ShrinkSynchronizationContextDispatcher(SynchronizationContext? context, int threadId)
|
||||
{
|
||||
_context = context;
|
||||
_threadId = threadId;
|
||||
}
|
||||
|
||||
public bool IsMainThread => Thread.CurrentThread.ManagedThreadId == _threadId;
|
||||
|
||||
public bool TryPost(Action action)
|
||||
{
|
||||
if (action == null)
|
||||
throw new ArgumentNullException(nameof(action));
|
||||
if (IsMainThread)
|
||||
{
|
||||
action();
|
||||
return true;
|
||||
}
|
||||
if (_context == null)
|
||||
return false;
|
||||
_context.Post(static state => ((Action)state!).Invoke(), action);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
Reference in New Issue
Block a user