lua协程实现异步编程模式
异步编程模式只是一个代码结构,c#中的async/await的写法就是异步编程模式,这边就是通过协程来达到和async/await类似的效果。
异步编程模式写法1:资源分帧加载
这边运行环境用的是:Unity+xLua
lua脚本:Assets/Lua/Test9.lua.txt
local _Time = CS.UnityEngine.Time local function WaitOneFrame() local co, isMain = coroutine.running() MonoInst:AddCallback(function() coroutine.resume(co) end) local result = coroutine.yield() end local function LoadOneResPerFrame() print("加载资源1, frame:", _Time.frameCount) WaitOneFrame() print("加载资源2, frame:", _Time.frameCount) WaitOneFrame() print("加载资源3, frame:", _Time.frameCount) end local co = coroutine.create(LoadOneResPerFrame) local isSucc, result = coroutine.resume(co) print("main end:", isSucc, result)
Test9.cs
public class Test9 : MonoBehaviour { private LuaEnv m_LuaEnv; private Queue<Action> m_PendingQueue = new Queue<Action>(); private Queue<Action> m_RunningQueue = new Queue<Action>(); void Start() { m_LuaEnv = new LuaEnv(); m_LuaEnv.AddLoader((ref string filePath) => { filePath = filePath.Replace('.', '/'); filePath = $"Assets/{filePath}.lua.txt"; var txtAsset = AssetDatabase.LoadAssetAtPath<TextAsset>(filePath); return Encoding.UTF8.GetBytes(txtAsset.text); }); m_LuaEnv.Global.Set("MonoInst", this); m_LuaEnv.DoString("require('Lua.Test9')"); } void OnDestroy() { if (null != m_LuaEnv) m_LuaEnv.Dispose(); } public void AddCallback(Action callback) { m_PendingQueue.Enqueue(callback); } void Update() { while (m_RunningQueue.Count > 0) { var act = m_RunningQueue.Dequeue(); act(); } while (m_PendingQueue.Count > 0) { var act = m_PendingQueue.Dequeue(); m_RunningQueue.Enqueue(act); } } }
运行结果: