在上一篇介绍了多线程和Unity交互方式,但是由于我的项目是一个unity编辑器插件项目,很显然上一篇的代码需要加以修改,在编辑器下实现Loom.
1,Editor下的没有Update这个生命周期函数,但是Ediitor提供了EditorApplication.update这个事件,自己用这个事件订阅update方法即可
2,Editor下的没有Awake OnDestory这些生命周期函数,需要自己编写方法让外部去创建、销毁Loom
3, 我的项目需要保证子线程逻辑不假死的同时又要保证同步,如下面这段伪代码,执行顺序为:DownFile1->UnityFunction1->DownFile2->UnityFunction2
Function
{
//异步在多线程下运行
Loom.RunAsync(() =>
{
//耗时函数
DownFile1();
//回到unity线程继续运行
Loom.QueueOnMainThread(()=>
{
//这个函数是unity函数
UnityFunction1();
}
//耗时函数
DownFile2();
//回到unity线程继续运行
Loom.QueueOnMainThread(()=>
{
//这个函数是unity函数
UnityFunction2();
}
}
}
修改后的代码如下
1 usingUnityEngine;2 usingSystem.Collections;3 usingSystem.Collections.Generic;4 usingSystem;5 usingSystem.Threading;6 usingSystem.Linq;7 usingUnityEditor;8 public classLoom9 {10 ///
11 ///当前是否有unity任务需要执行12 ///
13 static bool hasUnityAction = true;14
15 private staticThread loomThread;16
17 ///
18 ///unity任务表19 ///
20 private List actions = new List();21
22 #region 单例 注册update事件
23 private staticLoom _instance;24 private static readonly object lockObj = new object();25 public staticLoom Current26 {27 get
28 {29 if (_instance == null)30 {31 lock(lockObj)32 {33 if (_instance == null)34 {35 _instance = newLoom();36 }37
38 }39 }40 return_instance;41 }42 }43 privateLoom()44 {45 EditorApplication.update +=Update;46
47 }48 #endregion
49
50
51
52
53 ///
54 ///子线程启动一个任务55 ///
56 ///
57 ///
58 publicThread RunAsync(Action a)59 {60 if (loomThread != null)61 {62 Stop();63 throw new Exception("任务仅运行一次");64 }65 loomThread = new Thread(newParameterizedThreadStart(RunAction));66 loomThread.Name = "Loom线程";67 loomThread.Priority =System.Threading.ThreadPriority.Lowest;68 loomThread.Start(a);69 returnloomThread;70 }71 ///
72 ///加入一个任务到主线程队列73 ///
74 ///
75 public voidQueueOnMainThread(Action action)76 {77 if (Current != null && Thread.CurrentThread ==loomThread)78 {79 hasUnityAction = true;80 lock(Current.actions)81 {82 Current.actions.Add(action);83 }84 while(hasUnityAction)85 {86 loomThread.Priority =System.Threading.ThreadPriority.Lowest;87 Thread.Sleep(10);88 }89 }90
91 }92
93 ///
94 ///延迟子线程95 ///
96 ///
97 public void Sleep(inttime)98 {99 if (Current != null && Thread.CurrentThread ==loomThread)100 {101 Thread.Sleep(time);102
103 }104 }105
106 ///
107 ///停止任务108 ///
109 public voidStop()110 {111 EditorApplication.update -=Update;112 try
113 {114 loomThread.Abort();115 }116 catch(Exception e)117 {118 Debug.Log(e.ToString());119 }120 finally
121 {122 loomThread = null;123 _instance = null;124 }125
126 }127
128
129
130 private void RunAction(objectaction)131 {132 try
133 {134 ((Action)action)();135 }136 catch
137 {138 }139
140 }141
142 List _currentActions = new List();143
144 static voidUpdate()145 {146 try
147 {148
149
150 if (!hasUnityAction) return;151
152 lock(Current.actions)153 {154 Current._currentActions.Clear();155 Current._currentActions.AddRange(Current.actions);156 Current.actions.Clear();157 }158 for (int i = 0; i < Current._currentActions.Count; i++)159 {160 Debug.LogError("主线程任务");161 Current._currentActions[i]();162
163 }164 hasUnityAction = false;165 }166 catch
167 {168 Debug.LogError("主线程任务失败");169 }170 }171 }