前言
-
之前寫過一篇自動生成腳本的工具,但是我給它起名叫半自動代碼生成器,之所以稱之為半自動,因為我覺得全自動代碼生成器應該做到兩點:代碼生成+自動系結,之前的工具只做了代碼生成,并沒有做自動系結,所以鄙人又花時間研究了CocosCreator的預制體檔案,實作了自動系結的能力,并且支持了插件使用方式,
-
本篇內容,不僅僅是宣傳自己的插件工具,還會幫助大家分析一下Creator的預制體檔案格式,使購買插件的同學可以將插件價值最大化,也能讓讀者對Creator的預制體檔案有所了解,
Creator 預制體檔案格式分析
- 首先我們展示一小段預制體檔案,
[
{
"__type__": "cc.Prefab",
"_name": "",
"_objFlags": 0,
"_native": "",
"data": {
"__id__": 1
},
"optimizationPolicy": 0,
"asyncLoadAssets": false,
"readonly": false
},
{
"__type__": "cc.Node",
"_name": "LoginView",
"_objFlags": 0,
"_parent": null,
"_children": [
{
"__id__": 2
},
{
"__id__": 6
},
{
"__id__": 18
},
{
"__id__": 21
},
{
"__id__": 33
},
{
"__id__": 42
},
{
"__id__": 63
},
{
"__id__": 84
}
],
"_active": true,
"_components": [
{
"__id__": 105
},
{
"__id__": 106
}
],
"_prefab": {
"__id__": 107
},
"_opacity": 255,
"_color": {
"__type__": "cc.Color",
"r": 255,
"g": 255,
"b": 255,
"a": 255
},
"_contentSize": {
"__type__": "cc.Size",
"width": 960,
"height": 640
},
"_anchorPoint": {
"__type__": "cc.Vec2",
"x": 0.5,
"y": 0.5
},
"_trs": {
"__type__": "TypedArray",
"ctor": "Float64Array",
"array": [
480,
320,
0,
0,
0,
0,
1,
1,
1,
1
]
},
"_eulerAngles": {
"__type__": "cc.Vec3",
"x": 0,
"y": 0,
"z": 0
},
"_skewX": 0,
"_skewY": 0,
"_is3DNode": false,
"_groupIndex": 0,
"groupIndex": 0,
"_id": ""
}
]
-
當你第一次看到這個檔案的時候可能會有所疑惑,此檔案是一個一維陣列的json物件,
陣列第一個位置是預制體檔案的描述可以忽略,第二個位置的物件就是這個檔案根節點對應的屬性了,也是最重要的部分,從資料的_children 和_components欄位可以看出,引擎是根據__id__這個欄位來尋找其他資料的,只不過這個__id__并非你所理解的id,而是陣列的索引位置,并且配置中所有涉及到尋找其他資料都是用的這種__id__方式,包括給自己的腳本組件系結節點, -
由于我們是要匯出和系結其中的屬性,所以我們只關注__type__,_name,_childern,_components這幾個屬性就可以了,
-
__type__: 是一個比較重要的屬性,對于普通的組件,型別會是cc.Node,cc.Sprite,cc.Button之類的,對于腳本的型別比較特別,它并不是你定義的類名,而已一串經過處理的字符,但是它的特點就是長,所以我會用長度是否大于20來判斷是否是腳本組件,
下方是我已經做好系結腳本的配置內容,也說明如果你要給預制體添加腳本也就是給預制體的陣列添加一個下面格式的配置而已,通過下方的配置也可以看出我給這個腳本系結了start$VButton,login$VLabel,login$\VLabel,show$VRichText四個變數和testItem$ATestItemView一個陣列,
{
"__type__": "3e347nRcdVAiYpq6icd+8+w",
"_name": "",
"_objFlags": 0,
"node": {
"__id__": 1
},
"_enabled": true,
"start$VButton": {
"__id__": 14
},
"login$VLabel": {
"__id__": 19
},
"back$VButton": {
"__id__": 29
},
"show$VRichText": {
"__id__": 40
},
//系結的是一個陣列,長度為3
"testItem$ATestItemView": [
{
"__id__": 61
},
{
"__id__": 82
},
{
"__id__": 103
}
],
"_id": ""
},
- _name: 它是所有節點的名稱,注意,組件是沒有名稱的,所以我們處理檔案的時候也是從根節點深度遍歷所有的子節點,然后在遍歷節點的時候出理它的組件,
因為Creator的節點都是有名稱的,而且還有空格,支持重名,這些都是代碼生成器所不允許的,所以如果你想匯出一個屬性就要用特定的字符標識,
比如工具現在使用的是$V標識輸出的是一個變數,$A標識輸出的是一個陣列,當然陣列還需要名稱都相同,
var TAG = '$V'
var LIST = '$A'
當然這里邊還有一個問題就是一個節點可能掛了很多組件,那我們要怎么出理呢?
首先是做一個篩選,只有給定的組件才可以輸出
var NORMAL_COMP_LIST = ['cc.Label', 'cc.Sprite', 'cc.RichText', 'cc.Button', 'cc.ScrollView']
其次工具會將名稱后邊加上型別,以區別不同的組件的情況,
因此這也是一個可自定義和擴展的部分,
-
_children: 就是遍歷的節點,我們不用關心這個組態檔的陣列有多長,就從這些子節點深度遍歷就可以了,
-
_components: 遍歷每個節點的時候我們再遍歷一次它的所有組件,然后做上邊我們說的操作,這樣一個檔案走一遍之后我們的類需要的資訊也就生成了,
問題討論
-
既然腳本的型別是 "type": "3e347nRcdVAiYpq6icd+8+w",那么我們怎么找到對應的腳本檔案的名稱呢?
當你右鍵一個腳本檔案,點擊打開Library中的資源選項,會跳轉到一個js檔案中

這個檔案有四個特點,一是它的檔案名是你腳本的uuid.js,二是檔案帶有cc._RF.push(module,,三是帶有型別"3e347nRcdVAiYpq6icd+8+w",四是帶有腳本名稱,所以你只要查找檔案中帶有cc._RF.push(module,欄位并且帶有你傳入的型別的檔案并回傳后處理一下就可以獲得腳本名稱了,當然也可以得到路徑并做好import from 的設定,
這里可能有人會覺得,搜索整個imports路徑是不是很慢,其實不是,即使再慢還能比手動系結慢嗎?所以這個速度可以無視, -
怎么處理的creator自帶的meta機制,我是將代碼生成和自動系結分成兩個腳本,代碼生成之后會重繪生成腳本的目錄,然后再呼叫自動系結的腳本,重繪預制體目錄,
這里邊一直強調的就是重繪指定的目錄,而不是重繪整個assets或者整個Script,原因是我在使用的時候發現,重繪整個目錄會造成編輯器卡死,體驗很不好,所以當你不設定的腳本目錄不存在就做匯出時,creator顯示的目錄位置不是實際中硬碟中顯示的位置,重啟編輯器后才會正確,就是因為我重繪的目錄是你指定的目錄,如果指定的目錄不存在,目錄會創建,但是不會重繪,
重繪后的預制體檔案可能會報錯,可以無視,雙擊預制體檔案重新查看就可以了, -
如何做到系結嵌套的預制體的節點?
首先在匯出代碼的時候一旦遇到有腳本的節點就回傳,繼續遍歷其他子節點,這樣你的腳本里就不會宣告其他腳本要宣告的內容,
然后在系結的時候首先會找到應該做資料系結的腳本,然后再深入遍歷,當你發現你處理的這個節點上有腳本的時候就會用它身上腳本處理它的子節點,所以如果一個節點有多個腳本就只能系結第一個腳本的資料,
功能介紹
-
根據預制體檔案生成腳本

-
自定義輸入目錄和輸出目錄

-
自動系結屬性+陣列
使用$V標識變數
使用$A標識陣列
屬性名稱默認帶有型別,

-
自動系結button事件

-
可擴展匯出屬性型別

-
自動系結其他預制體的屬性,和button事件

-
自動匯入使用到的其他腳本

手懶不想自己實作的可以關注公眾號,進入微店購買,
歡迎掃碼關注公眾號《微笑游戲》,瀏覽更多內容,

歡迎掃碼關注公眾號《微笑游戲》,瀏覽更多內容,
轉載請註明出處,本文鏈接:https://www.uj5u.com/qita/669.html
標籤:其他
上一篇:使用四叉樹優化碰撞檢測
下一篇:小游戲云開發入門
