源文出自:https://zhuanlan.zhihu.com/p/91022294,进行修改了,针对自身项目进行修改了,本文为记录
此脚本挂到场景中:FileWatcher
using UnityEngine;
using System.IO;
using System.Collections;
using System.Collections.Generic;
/// <summary>
/// 监听文件改变
/// </summary>
public sealed class FileWatcher : MonoBehaviour
{
#if UNITY_EDITOR_WIN
class WatchInfo
{
FileSystemWatcher watcher;
string fileter;
List<string> changeFiles;
System.Action<string> changeAction;
string dirPath;
public WatchInfo(string _dirPath, string _filter, System.Action<string> _changeAction)
{
watcher = new FileSystemWatcher();
changeFiles = new List<string>();
fileter = _filter;
dirPath = _dirPath;
changeAction = _changeAction;
CreateWatcher(watcher, dirPath, changeFiles, fileter);
}
public void UpdateLs()
{
if (changeFiles.Count > 0 && null != changeAction)
{
foreach (var changeFile in changeFiles)
{
changeAction(changeFile);
}
changeFiles.Clear();
}
}
private void AddToLs(List<string> ls, string elem)
{
if (!ls.Contains(elem))
{
ls.Add(elem);
}
}
private void CreateWatcher(FileSystemWatcher watcher, string path, List<string> changeLs, string fileFilter)
{
CreateWatcher(watcher, path, fileFilter, (object source, FileSystemEventArgs e) =>
{
AddToLs(changeLs, e.FullPath);
}, (object source, RenamedEventArgs e) =>
{
AddToLs(changeLs, e.FullPath);
});
}
private void CreateWatcher(FileSystemWatcher watcher, string path, string fileFilter, FileSystemEventHandler onChanged, RenamedEventHandler onRenamed)
{
watcher.Path = Path.GetFullPath(path);
watcher.NotifyFilter = NotifyFilters.LastWrite;
watcher.Filter = fileFilter;
watcher.IncludeSubdirectories = true;
watcher.Changed += onChanged;
watcher.Created += onChanged;
watcher.Deleted += onChanged;
watcher.Renamed += onRenamed;
// Begin watching.
watcher.EnableRaisingEvents = true;
}
}
private static FileWatcher _instance;
private List<WatchInfo> watchInfos = new List<WatchInfo>();
public static void Create(GameObject go)
{
_instance = go.AddComponent<FileWatcher>();
}
string codePath = @"G:\AOE_SLG\logicenv\UnityLogic\Assets\LuaScripts";
IEnumerator Start()
{
watchInfos.Add(new WatchInfo(codePath, "*.lua", (changeCode) =>
{
string s = System.IO.Path.GetFileNameWithoutExtension(changeCode);//文件名
LuaInterface.LuaState L = LuaClient.GetMainState();
L.Call("OnCodeChange", s, true);//传入Lua中
}));
yield return null;
}
void LateUpdate()
{
foreach (var watcher in watchInfos)
{
watcher.UpdateLs();
}
}
# endif
}
这个Lua脚本要启动时加入呀.require(“HotCode”)
local function setFuncUpValue(newFunc, oldFunc)
local uvIndex = 1
while true do
local name, value = debug.getupvalue(oldFunc, uvIndex)
if name == nil then
break
end
debug.setupvalue(newFunc, uvIndex, value)
uvIndex = uvIndex + 1
end
end
function OnCodeChange(codePath)
for file, _ in pairs(package.loaded) do
local data = string.split(file, ".")
if IsListHasContains(data, codePath) then
local oldCodeObj = package.loaded[file]
package.loaded[file] = nil
xpcall(function()
local newCodeObj = require(file)
for k, v in pairs(newCodeObj) do
if type(v) == "function" and oldCodeObj[k] ~= v then
setFuncUpValue(v, oldCodeObj[k])
oldCodeObj[k] = v
end
end
end, function()
logerror(debug.traceback())
end)
package.loaded[file] = oldCodeObj
end
end
end