using System; using System.Collections.Concurrent; namespace XGame.Framework.ThreadScheduler { /// /// 线程调度 /// public static class ThreadSchedulers { private class TaskInfo { public Action Action; public object Context; public void Clear() { Action = null; Context = null; } } private static ConcurrentQueue _queueTasks = new ConcurrentQueue(); private static ConcurrentQueue _taskPool = new ConcurrentQueue(); public static void RunOnMainThread(Action action, object context) { var task = Get(); task.Action = action; task.Context = context; _queueTasks.Enqueue(task); } private static void Recycle(TaskInfo task) { if (task != null) { task.Clear(); _taskPool.Enqueue(task); } } private static TaskInfo Get() { if (!_taskPool.TryDequeue(out TaskInfo task)) task = new TaskInfo(); return task; } public static void Update() { while (_queueTasks.TryDequeue(out TaskInfo task)) { if (task != default) { try { task.Action.Invoke(task.Context); } catch (Exception e) { if (e.InnerException != null) { Log.Error($"[ThreadSchedulers] Message: {e.InnerException.Message},\n" + $"StackTrace: {e.InnerException.StackTrace}"); } else { Log.Error($"[ThreadSchedulers] Message: {e.Message} \n" + $"StackTrace: {e.StackTrace}"); } } finally { Recycle(task); } } } } public static void Dispose() { while (_queueTasks.TryDequeue(out var task)) ; while (_taskPool.TryDequeue(out var task)) ; } } }