1)AssetBundle異步加載被中斷的問(wèn)題
2)LuaDLL.lua_pcall()自身產(chǎn)生開(kāi)銷(xiāo)問(wèn)題
3)法線在手機(jī)渲染時(shí)出現(xiàn)的錯(cuò)誤問(wèn)題
4)UNITY_MATRIX_I_V 和Camera.main.worldToCameraMatrix.inverse區(qū)別
這是第272篇UWA技術(shù)知識(shí)分享的推送烁峭。今天我們繼續(xù)為大家精選了若干和開(kāi)發(fā)句柠、優(yōu)化相關(guān)的問(wèn)題,建議閱讀時(shí)間10分鐘常侣,認(rèn)真讀完必有收獲。
UWA 問(wèn)答社區(qū):answer.uwa4d.com
UWA QQ群2:793972859(原群已滿員)
Resources
Q:在使用異步接口yield return AssetBundle.ASyncLoad的時(shí)候弹渔,難免會(huì)想到:這個(gè)異步處理完之前如何Cancel掉這個(gè)任務(wù)胳施?也就是說(shuō)一個(gè)AssetBundle加載到一半,現(xiàn)在要放棄加載肢专,應(yīng)該怎么處理舞肆?
A1:其實(shí)底層調(diào)用GetAssetBundleBlocking,會(huì)在這個(gè)函數(shù)內(nèi)部調(diào)用PreloadManager的加載更新邏輯博杖,其實(shí)就是把Async操作改成了Sync了椿胯,會(huì)一直阻塞到AssetBundle加載成功。
但是也有坑剃根,這兒因?yàn)閳?zhí)行了PreloadManager.UpdatePreloading哩盲,內(nèi)部還會(huì)做GC。遇到過(guò)把不應(yīng)該卸載的資源給卸載了狈醉,說(shuō)是Unused廉油,但是實(shí)際正在使用。
感謝黃程@UWA問(wèn)答社區(qū)提供了回答
A2:資源加載管理的第一難題就是異步IO怎么被Cancel掉苗傅,或者說(shuō)從設(shè)計(jì)上怎么去實(shí)現(xiàn)等同的效果抒线。
但是相對(duì)于從Flash到Cocos到Unity來(lái)說(shuō),Unity還是做的很好的金吗。之前的任何引擎要處理好這個(gè)問(wèn)題十兢,非常之困難趣竣,需要很多代碼的支持,包括多線程更低層次的相關(guān)代碼旱物。這一塊Unity做得非常好遥缕,我們不用絞盡腦汁去實(shí)現(xiàn)異步IO Cancel的問(wèn)題,只需要做好上層架構(gòu)宵呛,設(shè)計(jì)出類似的功能单匣。
Unity的異步加載會(huì)返回一個(gè)Request對(duì)象,該對(duì)象有一個(gè)Get屬性AssetBundle宝穗,仔細(xì)查看該Get函數(shù)API會(huì)發(fā)現(xiàn)户秤。當(dāng)調(diào)用該屬性時(shí),會(huì)促使底層異步IO中斷(具體怎么實(shí)現(xiàn)的逮矛,有C++源碼的才能知道)鸡号,并立即同步加載該資源,且回調(diào)须鼎,回調(diào)順序是和你調(diào)用順序相當(dāng)?shù)模ū热绠惒郊虞d調(diào)用了2次并設(shè)置了回調(diào)鲸伴,現(xiàn)在觸發(fā)中斷并立即完成,會(huì)優(yōu)先回調(diào)異步設(shè)置的回調(diào))晋控。
所以基于這個(gè)設(shè)計(jì)一個(gè)好的引用計(jì)數(shù)器管理資源非常重要汞窗。
大部分項(xiàng)目的引用計(jì)數(shù)器設(shè)計(jì)都是待資源完成后添加引用計(jì)數(shù)。這種設(shè)計(jì)的適用場(chǎng)景非常局限赡译。在大型項(xiàng)目中使用環(huán)境非常復(fù)雜的資源加載情況下(異步加載中調(diào)用同步仲吏,異步加載中需要取消,異步加載中取消后立即同步等)會(huì)出現(xiàn)非常多的未知問(wèn)題和開(kāi)發(fā)中的局限性蝌焚,這種設(shè)計(jì)只適合微型項(xiàng)目快速開(kāi)發(fā)裹唆。
所以一個(gè)完備的引用計(jì)數(shù)設(shè)計(jì)應(yīng)該是調(diào)用加載方法時(shí),就生成該資源未來(lái)被加載完成后的數(shù)據(jù)殼子综看,并添加引用計(jì)數(shù)(因?yàn)榧虞d本身其實(shí)也是一次引用品腹,包括bundle.AsynLoadAsset,其實(shí)任何的異步加載自身都需要添加一次引用红碑,防止上層代碼的邏輯舞吭,造成引用計(jì)數(shù)器非法=0觸發(fā)bundle.unload方法),完成后減少引用計(jì)數(shù)析珊。那么同步加載時(shí)需要查找數(shù)據(jù)殼子羡鸥,如果該資源正在異步加載,需要調(diào)用其request.assetBundle讓其立即中斷異步并立即同步完成加載忠寻。(否則同步加載時(shí)底層會(huì)拋出警告惧浴。)
基于這個(gè)我們可以設(shè)計(jì)一套非常完備的Cancel系統(tǒng),上層調(diào)用Cancel時(shí)奕剃,其實(shí)就是讓其外部引用-1衷旅,因?yàn)槔碚撋衔覀兡苣玫降乃薪涌跓o(wú)法真正中斷一次IO捐腿,只有待其加載完成后,發(fā)現(xiàn)引用計(jì)數(shù)等于0時(shí)柿顶,才會(huì)Unload掉資源茄袖。
設(shè)計(jì)思路這里只是拋出一點(diǎn),具體怎么去實(shí)現(xiàn)和設(shè)計(jì)各抒己見(jiàn)嘁锯。只是如果一個(gè)資源管理器不能適應(yīng)任何(絕大部分)加載情形宪祥,那么這還是一個(gè)資源管理器嗎?
感謝1 9 7 3-311135@UWA問(wèn)答社區(qū)提供了回答家乘,歡迎大家轉(zhuǎn)至社區(qū)交流:
https://answer.uwa4d.com/question/5af3db530e95a527a7a81d31
Lua
Q:為什么LuaDLL.lua_pcall()自身會(huì)產(chǎn)生這么大的開(kāi)銷(xiāo)蝗羊?
A1:是不是Lua自身邏輯消耗比較高,這個(gè)可以看Lua側(cè)的消耗:《Lua Profiler——快速定位Lua性能問(wèn)題》仁锯。
感謝jjjzzz@UWA問(wèn)答社區(qū)提供了回答
A2:lua_pcall只是通過(guò)壓棧的方式調(diào)用了Lua耀找,具體消耗還得在Lua那邊看看,估計(jì)是某函數(shù)C#和Lua瘋狂調(diào)用比較厲害业崖。
感謝蕭小俊@UWA問(wèn)答社區(qū)提供了回答
A3:用DeepProfile才能知道具體是哪個(gè)方法調(diào)用高涯呻,這里只是C# call到Lua,后面的棧信息已經(jīng)沒(méi)有了腻要,不能單純的說(shuō)LuaDLL.lua_pcall()開(kāi)銷(xiāo)大。
感謝1 9 7 3-311135@UWA問(wèn)答社區(qū)提供了回答涝登,歡迎大家轉(zhuǎn)至社區(qū)交流:
https://answer.uwa4d.com/question/606184ecafbc233466c02c80
Rendering
Q:法線在手機(jī)渲染時(shí)出現(xiàn)的錯(cuò)誤問(wèn)題:
用的版本是Unity 2019.4 URP雄家。Editor模式下是正確的,在默認(rèn)Unity Build的打包正確胀滚,將資源打成AssetBundle后渲染出現(xiàn)錯(cuò)誤趟济。Shader使用了多種,包括默認(rèn)的Lit Shader咽笼,都會(huì)出現(xiàn)該問(wèn)題顷编。
A:懷疑是渲染管線的Shader問(wèn)題,變體收集問(wèn)題剑刑,最后一一排除后變成Mesh問(wèn)題媳纬。有好大哥MoMo的奶爸告訴我,Unity部分版本的Optimize Mesh Data選項(xiàng)默認(rèn)打開(kāi)施掏,會(huì)優(yōu)化掉部分網(wǎng)格钮惠,導(dǎo)致以上的問(wèn)題。
感謝題主霸氣九號(hào)@UWA問(wèn)答社區(qū)提供了回答七芭,歡迎大家轉(zhuǎn)至社區(qū)交流:
https://answer.uwa4d.com/question/616e6d248f8c834241e4f742
Rendering
Q:URP中Shader的UNITY_MATRIX_I_V 和C#中Camera.main.worldToCameraMatrix.inverse獲取到的矩陣并不一樣素挽,在Shader中用ViewSpace的坐標(biāo)乘以UNITY_MATRIX_I_V并不能夠得到正確的世界坐標(biāo),乘以Camera.main.worldToCameraMatrix.inverse則可以狸驳,請(qǐng)問(wèn)他們二者的區(qū)別是什么呢预明?
A:我這邊做的測(cè)試并沒(méi)有發(fā)現(xiàn)這兩個(gè)矩陣有什么不同缩赛。
在Shader中修改Frag來(lái)調(diào)用UNITY_MATRIX_I_V:
在C#中打印這個(gè)矩陣,從Frame Debugger和控制臺(tái)輸出的結(jié)果來(lái)看這兩個(gè)矩陣沒(méi)有什么不同撰糠。
使用URP的Shader Simple Lit酥馍,計(jì)算逆矩陣之后的結(jié)果也是一致的:
感謝宗卉軒@UWA問(wèn)答社區(qū)提供了回答,歡迎大家轉(zhuǎn)至社區(qū)交流:
https://answer.uwa4d.com/question/616d6b2c8f8c834241e38f1d
20211025
更多精彩問(wèn)題等你回答~
Unity增量打包AssetBundle沒(méi)變化的資源也會(huì)被重新打包
在模型有UV2的情況下開(kāi)啟Generate Lightmap UVs
封面圖來(lái)源于網(wǎng)絡(luò)
今天的分享就到這里窗慎。當(dāng)然物喷,生有涯而知無(wú)涯。在漫漫的開(kāi)發(fā)周期中遮斥,您看到的這些問(wèn)題也許都只是冰山一角峦失,我們?cè)缫言赨WA問(wèn)答網(wǎng)站上準(zhǔn)備了更多的技術(shù)話題等你一起來(lái)探索和分享。歡迎熱愛(ài)進(jìn)步的你加入术吗,也許你的方法恰能解別人的燃眉之急尉辑;而他山之“石”,也能攻你之“玉”较屿。
官網(wǎng):www.uwa4d.com
官方技術(shù)博客:blog.uwa4d.com
官方問(wèn)答社區(qū):answer.uwa4d.com
UWA學(xué)堂:edu.uwa4d.com
官方技術(shù)QQ群:793972859(原群已滿員)