首页 > 编程知识 正文

滑板类型和入门知识,小说入门类型

时间:2023-05-06 07:58:12 阅读:270383 作者:4070

简介

在ILRuntime中,如果不对Unity特定数据类型进行绑定,也是可以使用的,但是会产生较多额外的CPU开销和GC。我们只需要在热更使用前,对需要用的Unity特殊数据类型进行绑定后就能高性能简单使用了。

使用流程说明 和之前文章一样初始化appdomain //大家在正式项目中请全局只创建一个AppDomain AppDomain appdomain; System.IO.MemoryStream fs; System.IO.MemoryStream p; void Start() { StartCoroutine(LoadHotFixAssembly()); } IEnumerator LoadHotFixAssembly() { //首先实例化ILRuntime的AppDomain,AppDomain是一个应用程序域,每个AppDomain都是一个独立的沙盒 appdomain = new ILRuntime.Runtime.Enviorment.AppDomain(); //正常项目中应该是自行从其他地方下载dll,或者打包在AssetBundle中读取,平时开发以及为了演示方便直接从StreammingAssets中读取, //正式发布的时候需要大家自行从其他地方读取dll //!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! //这个DLL文件是直接编译HotFix_Project.sln生成的,已经在项目中设置好输出目录为StreamingAssets,在VS里直接编译即可生成到对应目录,无需手动拷贝#if UNITY_ANDROID WWW www = new WWW(Application.streamingAssetsPath + "/HotFix_Project.dll");#else WWW www = new WWW("file:///" + Application.streamingAssetsPath + "/HotFix_Project.dll");#endif while (!www.isDone) yield return null; if (!string.IsNullOrEmpty(www.error)) UnityEngine.Debug.LogError(www.error); byte[] dll = www.bytes; www.Dispose(); //PDB文件是调试数据库,如需要在日志中显示报错的行号,则必须提供PDB文件,不过由于会额外耗用内存,正式发布时请将PDB去掉,下面LoadAssembly的时候pdb传null即可#if UNITY_ANDROID www = new WWW(Application.streamingAssetsPath + "/HotFix_Project.pdb");#else www = new WWW("file:///" + Application.streamingAssetsPath + "/HotFix_Project.pdb");#endif while (!www.isDone) yield return null; if (!string.IsNullOrEmpty(www.error)) UnityEngine.Debug.LogError(www.error); byte[] pdb = www.bytes; fs = new MemoryStream(dll); p = new MemoryStream(pdb); try { appdomain.LoadAssembly(fs, p, new ILRuntime.Mono.Cecil.Pdb.PdbReaderProvider()); } catch { Debug.LogError("加载热更DLL失败,请确保已经通过VS打开Assets/Samples/ILRuntime/1.6/Demo/HotFix_Project/HotFix_Project.sln编译过热更DLL"); }#if DEBUG && (UNITY_EDITOR || UNITY_ANDROID || UNITY_IPHONE) //由于Unity的Profiler接口只允许在主线程使用,为了避免出异常,需要告诉ILRuntime主线程的线程ID才能正确将函数运行耗时报告给Profiler appdomain.UnityMainThreadID = System.Threading.Thread.CurrentThread.ManagedThreadId;#endif InitializeILRuntime(); OnHotFixLoaded(); } Unity类中注册热更新要使用的特殊类型 void InitializeILRuntime() { //这里做一些ILRuntime的注册,这里我们注册值类型Binder,注释和解注下面的代码来对比性能差别 appdomain.RegisterValueTypeBinder(typeof(Vector3), new Vector3Binder()); appdomain.RegisterValueTypeBinder(typeof(Quaternion), new QuaternionBinder()); appdomain.RegisterValueTypeBinder(typeof(Vector2), new Vector2Binder()); } Unity类中测试使用热更工程中的特殊变量方法 void OnHotFixLoaded() { StartCoroutine(_onHotFixLoaded()); } IEnumerator _onHotFixLoaded() { yield return new WaitForSeconds(0.5f); RunTest(); yield return new WaitForSeconds(0.5f); RunTest2(); yield return new WaitForSeconds(0.5f); RunTest3(); } void RunTest() { Debug.Log("Vector3等Unity常用值类型如果不做任何处理,在ILRuntime中使用会产生较多额外的CPU开销和GC Alloc"); Debug.Log("我们通过值类型绑定可以解决这个问题,只有Unity主工程的值类型才需要此处理,热更DLL内定义的值类型不需要任何处理"); //调用无参数静态方法,appdomain.Invoke("类名", "方法名", 对象引用, 参数列表); appdomain.Invoke("HotFix_Project.TestValueType", "RunTest", null, null); } void RunTest2() { Debug.Log("======================================="); Debug.Log("Quaternion测试"); //调用无参数静态方法,appdomain.Invoke("类名", "方法名", 对象引用, 参数列表); appdomain.Invoke("HotFix_Project.TestValueType", "RunTest2", null, null); } void RunTest3() { Debug.Log("======================================="); Debug.Log("Vector2测试"); //调用无参数静态方法,appdomain.Invoke("类名", "方法名", 对象引用, 参数列表); appdomain.Invoke("HotFix_Project.TestValueType", "RunTest3", null, null); } 热更工程中使用特殊变量类型的测试类和方法变量 class TestValueType { public static void RunTest() { System.Diagnostics.Stopwatch sw = new System.Diagnostics.Stopwatch(); //Debug.Log("测试Vector3的各种运算"); Vector3 a = new Vector3(1, 2, 3); Vector3 b = Vector3.one; Debug.Log("a + b = " + (a + b)); Debug.Log("a - b = " + (a - b)); Debug.Log("a * 2 = " + (a * 2)); Debug.Log("2 * a = " + (2 * a)); Debug.Log("a / 2 = " + (a / 2)); Debug.Log("-a = " + (-a)); Debug.Log("a == b = " + (a == b)); Debug.Log("a != b = " + (a != b)); Debug.Log("a dot b = " + Vector3.Dot(a, b)); Debug.Log("a cross b = " + Vector3.Cross(a, b)); Debug.Log("a distance b = " + Vector3.Distance(a, b)); Debug.Log("a.magnitude = " + a.magnitude); Debug.Log("a.normalized = " + a.normalized); Debug.Log("a.sqrMagnitude = " + a.sqrMagnitude); sw.Start(); float dot = 0; for(int i = 0; i < 100000; i++) { a += Vector3.one; dot += Vector3.Dot(a, Vector3.zero); } sw.Stop(); Debug.LogFormat("Value: a={0},dot={1}, time = {2}ms", a, dot, sw.ElapsedMilliseconds); } public static void RunTest2() { System.Diagnostics.Stopwatch sw = new System.Diagnostics.Stopwatch(); //Debug.Log("测试Vector3的各种运算"); Quaternion a = new Quaternion(1, 2, 3, 4); Quaternion b = Quaternion.identity; Vector3 c = new Vector3(2, 3, 4); Debug.Log("a * b = " + (a * b)); Debug.Log("a * c = " + (a * c)); Debug.Log("a == b = " + (a == b)); Debug.Log("a != b = " + (a != b)); Debug.Log("a dot b = " + Quaternion.Dot(a, b)); Debug.Log("a angle b = " + Quaternion.Angle(a, b)); Debug.Log("a.eulerAngles = " + a.eulerAngles); Debug.Log("Quaternion.Euler(c) = " + Quaternion.Euler(c)); Debug.Log("Quaternion.Euler(2,3,4) = " + Quaternion.Euler(2, 3, 4)); sw.Start(); var rot = Quaternion.Euler(c); float dot = 0; for (int i = 0; i < 100000; i++) { a *= rot; dot += Quaternion.Dot(a, b); } sw.Stop(); Debug.LogFormat("Value: a={0},dot={1}, time = {2}ms", a, dot, sw.ElapsedMilliseconds); } public static void RunTest3() { System.Diagnostics.Stopwatch sw = new System.Diagnostics.Stopwatch(); //Debug.Log("测试Vector2的各种运算"); Vector2 a = new Vector2(1, 2); Vector2 b = Vector2.one; Debug.Log("a + b = " + (a + b)); Debug.Log("a - b = " + (a - b)); Debug.Log("a * 2 = " + (a * 2)); Debug.Log("2 * a = " + (2 * a)); Debug.Log("a / 2 = " + (a / 2)); Debug.Log("-a = " + (-a)); Debug.Log("a == b = " + (a == b)); Debug.Log("a != b = " + (a != b)); Debug.Log("(Vector3)a = " + ((Vector3)a)); Debug.Log("(Vector2)Vector3.one = " + ((Vector2)Vector3.one)); Debug.Log("a dot b = " + Vector2.Dot(a, b)); Debug.Log("a distance b = " + Vector2.Distance(a, b)); Debug.Log("a.magnitude = " + a.magnitude); Debug.Log("a.normalized = " + a.normalized); Debug.Log("a.sqrMagnitude = " + a.sqrMagnitude); sw.Start(); float dot = 0; for (int i = 0; i < 100000; i++) { a += Vector2.one; dot += Vector2.Dot(a, Vector2.zero); } sw.Stop(); Debug.LogFormat("Value: a={0},dot={1}, time = {2}ms", a, dot, sw.ElapsedMilliseconds); } }

就是那么简单,之前文章中类型的绑定也有使用到,大家用Unity特殊变量类型时注意绑定一下就行。根据官方Demo来的教程到这里就结束了,基本已经满足了绝大部分项目的开发需求了,有问题可以加ILRuntime开发者蓝大的QQ群大家一起讨论。

版权声明:该文观点仅代表作者本人。处理文章:请发送邮件至 三1五14八八95#扣扣.com 举报,一经查实,本站将立刻删除。