前言
論壇上有很多文章、很多人說Creator大項目卡頓,也在苦苦尋找解決方案。
這對于每一個想用
Creator
做個大項目或者正在做着項目的小夥伴來說都是很難受的。
這可能會讓他們割舍對Creator的喜愛,而另作選擇。
或者在上了車之後,沒法填這個坑導緻項目黃了,那就更加難過了。
怎麼辦呢?我過年時就萌生了一個想法:我想摸一下Creator的上限。看看到底能不能解決大項目卡頓的問題,也是替各位小夥伴們探探路。
前段時間的探索,成功了。
那讓我知道Creator開發大項目是完全沒有問題的。
可以讓我們用Creator爽,一直用一直爽的。
![](https://img.laitimes.com/img/__Qf2AjLwojIjJCLyojI0JCLiYWan5CMwQmN5QGM5YWN0EmZiRWZxEmY4IjYwQWOlJWYwcTO18CX0JXZ252bj91Ztl2Lc52YucWbp5GZzNmLn9Gbi1yZtl2Lc9CX6MHc0RHaiojIsJye.gif)
文章:
我想摸一下Creator的上限
上個星期有個深陷水深火熱的小夥伴找到我,讓我幫幫忙
能夠幫到他,非常開心。
最近項目趕版本,比較忙,是以解決方案完善的進度慢了些。
雖遲但到~
視訊示範:
https://www.bilibili.com/video/BV1hh411e7p5/
插件位址:
https://store.cocos.com/app/resources/search?name=Aswallow
我們感到難受的是什麼?
先說開發過程中讓人感覺很舒服的一種情況
我改了一行代碼,立刻就能看到運作情況
讓人感覺難受的是什麼?
我改了一行代碼,等了好久都沒能運作起來
回報的時間越短,越舒服
其實這裡有一個很有趣的概念,叫
即時回報
,它是進入心流狀态的條件之一(就是那種很爽很沉醉的狀态)
有興趣的可以查一下。
CocosCreator
讓我們在開發遊戲過程中,能快速得到回報
- 編輯場景,儲存一下就可以重新整理看結果
- 改一下代碼,立刻編譯看結果
- 修改shader立刻也能看到效果
- 遇到難點、bug翻一下論壇就能找到解決方案
這個就很舒服
但項目資源越多,這個改了一行代碼,卡的時間就越長,越來越難受。
而項目後期大部分時間可能都是在改代碼,也就意味着,一直卡。像吃屎一樣。
其實。。。
其實很多引擎在項目資源多的時候都會出現卡頓、回報時間長等問題,這個是通病。
有問題就解決嘛。我們先找找原因
另外:
CocosCreator
已經做得很好了,不是嗎?
卡頓的根源:Creator編輯器的資源管理機制
Creator
編輯器會對所有資源進行分析,記錄它們之間的依賴關系。
.meta
檔案就是記錄資源的資訊和依賴資訊
資源的修改、增加、删除,都可能會導緻依賴資訊變化。
是以Creator會監視所有assets目錄下的檔案,當某個資源變動,編輯器都會周遊檢查一下變動的影響。
這是為了保證依賴的準确性,如果依賴缺失了就會立刻提示你。
是以,當資源量多了,這個處理耗時就會變得越來越長。
這也是以下情況的緣由
- 儲存一下prefab,卡頓好久
- 儲存一下代碼,切回來卡了好久
正所謂成也蕭何敗也蕭何
解決思路:拆
論壇上其實就有這個思路的方案,比如
- 将圖檔預先打成圖集=>減少圖檔資源量
- 将資源放到CDN
Creator官方在
Creator2.4.x
版本也給出了他們的解決方案:AssetBundle
我覺得,在項目内分AssetBundle,卡頓問題還是沒法解決的。因為資源量沒變,處理耗時也也沒有減少
但如果在另外一個項目制作資源的
AssetBundle
,然後導出。這個是可以解決問題的。
這些方案是有用,但就是有些麻煩,怎麼才能做到更加友善和無感覺呢?
而且還有一個問題,怎麼加載解析
圖集
、
龍骨
、
spine
甚至
fgui釋出的資源
和
tilemap
呢?
因為官方的接口中,加載遠端資源:隻能加載簡單的圖檔、音頻、文本
文檔傳送門🚪:
https://docs.cocos.com/creator/manual/zh/scripting/dynamic-load-resources.html
我的解決方案
拆分資源的解決方案
第一種:自定義網頁預覽
不知道大家知不知道這個的存在。
文檔傳送門:
https://docs.cocos.com/creator/manual/zh/advanced-topics/custom-preview-template.html
在項目根目錄建立
preview-templates
,然後編輯器的預覽功能就會以這個目錄為入口
你将外部資源放到這個檔案夾,使用遠端加載接口,就可以加載到這裡的資源
//直接将someres.png放到preview-templates
var remoteUrl = "someres.png";
cc.assetManager.loadRemote(remoteUrl, function (err, texture) {
// Use texture to create sprite frame
});
但這樣需要自己在建構時處理資源,複制到釋出目錄
第二種:插件 aswallow 如燕(諧音:愛上我咯)
-
開發預覽支援
我通過hook creator的預覽伺服器邏輯,讓你可以通路assets檔案夾外的目錄。對原來的預覽伺服器邏輯無影響
你隻需将需要拆分出去的資源放到assets檔案夾外的ext-res檔案夾内即可
這個ext-res也可以通過修改local/aswallow-config.json來修改
-
釋出建構支援
建構時,會自動将資源拷貝到建構輸出目錄,建構配置中的MD5Cache打開可以給檔案名加md5,生成路徑映射version.json檔案
也可以自己實作自定義的建構處理邏輯,具體可見custom-build-scripts/custom-build.js
建構功能支援Creator2.3.x和2.4.x,以及釋出建構支援:微信小遊戲(其他小遊戲沒測,應該可以)、安卓原生、web
當然,如果配合下面的這個運作時會更完美
ps:聽jare大佬說Assetbundle可以單獨釋出,我沒找到。不過将資源項目釋出到ext-res檔案夾,就可以遠端加載其中的bundle資源了
複雜資源加載解析方案
這個其實挺苦惱的,官方沒有接口。
我在論壇找到了龍骨的加載解析邏輯,然後斷點運作看源碼完善了。圖集、spine、tilemap也是斷點運作看源碼實作的。
找到了解析方法後,基于此實作了
aswallow-asset-manager
它可以讓你更加簡單的加載、解析和管理
外部資源
(圖集、龍骨、spine、tilemap、fgui釋出的資源)
通過加載version檔案,可以實作輕易加載解析加了md5字尾的資源(加載邏輯不變的情況下)
使用示例:
- 加載圖集
aswallow.extAssetMgr.load([{ url: "atlas/emoji", assetType: "plist" }], (err, result) => { console.log(result); const atlas = aswallow.extAssetMgr.get("atlas/emoji.plist") as cc.SpriteAtlas; console.log(atlas); this.emojiSp.spriteFrame = atlas.getSpriteFrame("emoji1") }); }
- 加載圖檔
let asset: cc.Asset; let index = 0; this._scheduleCallback = () => { asset = aswallow.extAssetMgr.get(`${iconRoot}/i${index}.png`); index = Math.floor(Math.random() * 10); this.sp.spriteFrame = null; this.sp.spriteFrame = new cc.SpriteFrame(asset as cc.Texture2D); } let iconRoot = "fgui-res/Icons"; let resPaths = []; for (let i = 0; i < 10; i++) { resPaths.push(iconRoot + "/i" + i + ".png"); } // cc.assetManager.preloadAny() aswallow.extAssetMgr.load(resPaths, (err, result: aswallow.ILoadResult) => { if (!err) { console.log(`加載成功`) console.log(result); this.schedule(this._scheduleCallback, 1, cc.macro.REPEAT_FOREVER); // this.sp.spriteFrame.ensureLoadTexture(); } });
- 加載龍骨
const extAssetMgr = aswallow.extAssetMgr; extAssetMgr.load([ { url: "dragonbones/dragon/texture.json", assetType: "DragonBonesAtlasAsset" }, { url: "dragonbones/dragon/NewDragonTest.json", assetType: "DragonBonesAsset" }, "dragonbones/dragon/texture.png"], (err, items) => { console.log(items) this.dragonBone_json.dragonAsset = extAssetMgr.get("dragonbones/dragon/NewDragonTest.json") as any; this.dragonBone_json.dragonAtlasAsset = extAssetMgr.get("dragonbones/dragon/texture.json") as any; this.dragonBone_json.armatureName = 'armatureName'; this.dragonBone_json.playAnimation('stand', 0); }); //加載二進制 extAssetMgr.load({ url: "dragonbones/sword-man/SwordsMan", assetType: "DragonBonesAsset", ext: ".dbbin" }, (err, items) => { this.dragonBone_bin.dragonAsset = extAssetMgr.get("dragonbones/sword-man/SwordsMan_ske.dbbin") as any; this.dragonBone_bin.dragonAtlasAsset = extAssetMgr.get("dragonbones/sword-man/SwordsMan_tex.json") as any; this.dragonBone_bin.armatureName = 'Swordsman-NestArmature'; this.dragonBone_bin.playAnimation('walk', 0); })
- 加載spine
const extAssetMgr = aswallow.extAssetMgr; extAssetMgr.load([{ url: "spines/spineboy/spineboy.json", assetType: "SpineAsset" }, "spines/spineboy/spineboy.txt", "spines/spineboy/spineboy.png"], (err, items) => { console.log(items) this.spine_json.skeletonData = extAssetMgr.get("spines/spineboy/spineboy.json") as any; this.spine_json.animation = 'run'; }); //加載二進制 extAssetMgr.load([{ url: "spines/spineRatorBin/raptor-pro.skel", assetType: "SpineAsset" }, "spines/spineRatorBin/raptor-pro.atlas", "spines/spineRatorBin/raptor-pro.png"], (err, items) => { console.log(items) this.spine_bin.skeletonData = extAssetMgr.get("spines/spineRatorBin/raptor-pro.skel") as any; this.spine_bin.animation = 'walk'; // this.spine._updateSkeletonData });
- 加載fgui
- 資源釋放(以釋放spine資源為例)
aswallow.extAssetMgr.release([ { url: "spines/spineboy/spineboy.json", assetType: "SpineAsset" }, "spines/spineboy/spineboy.txt", "spines/spineboy/spineboy.png", { url: "spines/spineRatorBin/raptor-pro.skel", assetType: "SpineAsset" }, "spines/spineRatorBin/raptor-pro.atlas", "spines/spineRatorBin/raptor-pro.png" ])
暫時支援2.4.x,釋出建構測試通過的平台:Android原生、web、微信小遊戲(其他小遊戲平台應該也可以)
最後
CocosCreator其實是很強大的,不是嗎?
卡頓問題也是可以輕易解決的,不是嗎?
希望每個喜愛Cocos的小夥伴不用糾結要不要用Creator開發大項目
希望在開發大項目的小夥伴不再受卡頓之苦
希望每個CocosCreator項目都有所成~
能幫到你們真的很開心。
如果喜歡我的解決方案,想一起玩轉遊戲開發
歡迎關注我的公衆号
公衆号搜尋:玩轉遊戲開發
或掃碼:
QQ 群: 1103157878
部落格首頁: https://ailhc.github.io/
掘金: https://juejin.cn/user/3069492195769469
github: https://github.com/AILHC