cocos2d-cli 1.6.5 → 2.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/data/script_map.json +25 -25
- package/dist/bin/cocos2d-cli.js +64 -0
- package/dist/src/commands/add-component.js +3 -0
- package/dist/src/commands/add.js +3 -0
- package/dist/src/commands/build.js +6 -0
- package/dist/src/commands/create-scene.js +3 -0
- package/dist/src/commands/get.js +3 -0
- package/dist/src/commands/prefab-create.js +109 -0
- package/dist/src/commands/remove-component.js +3 -0
- package/dist/src/commands/remove.js +3 -0
- package/dist/src/commands/screenshot.js +41 -0
- package/dist/src/commands/set-component.js +3 -0
- package/dist/src/commands/set.js +3 -0
- package/dist/src/commands/tree.js +24 -0
- package/{src → dist/src}/lib/cc/CCButton.js +115 -122
- package/{src → dist/src}/lib/cc/CCCamera.js +83 -93
- package/{src → dist/src}/lib/cc/CCCanvas.js +49 -54
- package/{src → dist/src}/lib/cc/CCColor.js +30 -32
- package/{src → dist/src}/lib/cc/CCComponent.js +39 -60
- package/{src → dist/src}/lib/cc/CCLabel.js +139 -146
- package/{src → dist/src}/lib/cc/CCNode.js +190 -256
- package/{src → dist/src}/lib/cc/CCObject.js +19 -23
- package/{src → dist/src}/lib/cc/CCPrefab.js +219 -242
- package/{src → dist/src}/lib/cc/CCRect.js +30 -32
- package/{src → dist/src}/lib/cc/CCRichText.js +38 -44
- package/{src → dist/src}/lib/cc/CCScene.js +32 -42
- package/dist/src/lib/cc/CCSceneAsset.js +242 -0
- package/{src → dist/src}/lib/cc/CCSize.js +22 -26
- package/{src → dist/src}/lib/cc/CCSprite.js +82 -94
- package/{src → dist/src}/lib/cc/CCTrs.js +49 -74
- package/{src → dist/src}/lib/cc/CCVec2.js +22 -26
- package/{src → dist/src}/lib/cc/CCVec3.js +26 -29
- package/{src → dist/src}/lib/cc/CCWidget.js +94 -98
- package/dist/src/lib/fire-utils.js +86 -0
- package/dist/src/lib/json-parser.js +114 -0
- package/dist/src/lib/node-utils.js +131 -0
- package/{src → dist/src}/lib/screenshot-core.js +242 -285
- package/dist/src/lib/templates.js +17 -0
- package/dist/src/lib/utils.js +81 -0
- package/package.json +40 -33
- package/bin/cocos2d-cli.js +0 -152
- package/src/commands/add-component.js +0 -112
- package/src/commands/add.js +0 -177
- package/src/commands/build.js +0 -78
- package/src/commands/create-scene.js +0 -181
- package/src/commands/get.js +0 -108
- package/src/commands/prefab-create.js +0 -111
- package/src/commands/remove-component.js +0 -111
- package/src/commands/remove.js +0 -99
- package/src/commands/screenshot.js +0 -108
- package/src/commands/set-component.js +0 -119
- package/src/commands/set.js +0 -107
- package/src/commands/tree.js +0 -29
- package/src/lib/cc/CCSceneAsset.js +0 -303
- package/src/lib/cc/index.js +0 -42
- package/src/lib/fire-utils.js +0 -374
- package/src/lib/json-parser.js +0 -185
- package/src/lib/node-utils.js +0 -395
- package/src/lib/screenshot/favicon.ico +0 -0
- package/src/lib/screenshot/index.html +0 -30
- package/src/lib/templates.js +0 -49
- package/src/lib/utils.js +0 -202
package/src/lib/fire-utils.js
DELETED
|
@@ -1,374 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Fire/Prefab 文件工具模块
|
|
3
|
-
* 提供场景/预制体文件的读写和编辑器交互功能
|
|
4
|
-
*/
|
|
5
|
-
|
|
6
|
-
const fs = require('fs');
|
|
7
|
-
const path = require('path');
|
|
8
|
-
const crypto = require('crypto');
|
|
9
|
-
|
|
10
|
-
/**
|
|
11
|
-
* 检测是否为预制体文件
|
|
12
|
-
*/
|
|
13
|
-
function isPrefab(data) {
|
|
14
|
-
return data[0]?.__type__ === 'cc.Prefab';
|
|
15
|
-
}
|
|
16
|
-
|
|
17
|
-
/**
|
|
18
|
-
* 加载场景/预制体文件
|
|
19
|
-
*/
|
|
20
|
-
function loadScene(scenePath) {
|
|
21
|
-
if (!fs.existsSync(scenePath)) {
|
|
22
|
-
throw new Error(`文件不存在: ${scenePath}`);
|
|
23
|
-
}
|
|
24
|
-
|
|
25
|
-
const content = fs.readFileSync(scenePath, 'utf8');
|
|
26
|
-
return JSON.parse(content);
|
|
27
|
-
}
|
|
28
|
-
|
|
29
|
-
/**
|
|
30
|
-
* 保存场景/预制体文件
|
|
31
|
-
*/
|
|
32
|
-
function saveScene(scenePath, data) {
|
|
33
|
-
fs.writeFileSync(scenePath, JSON.stringify(data, null, 2), 'utf8');
|
|
34
|
-
}
|
|
35
|
-
|
|
36
|
-
/**
|
|
37
|
-
* 构建 ID 和索引映射
|
|
38
|
-
*/
|
|
39
|
-
function buildMaps(data) {
|
|
40
|
-
const idMap = {};
|
|
41
|
-
const indexMap = {};
|
|
42
|
-
const prefab = isPrefab(data);
|
|
43
|
-
|
|
44
|
-
function traverse(nodeIndex, parentPath = '') {
|
|
45
|
-
const node = data[nodeIndex];
|
|
46
|
-
if (!node) return;
|
|
47
|
-
|
|
48
|
-
if (!node.__type__?.startsWith('cc.Node') && node.__type__ !== 'cc.Scene') {
|
|
49
|
-
return;
|
|
50
|
-
}
|
|
51
|
-
|
|
52
|
-
const nodeId = node._id;
|
|
53
|
-
if (nodeId) {
|
|
54
|
-
idMap[nodeId] = nodeIndex;
|
|
55
|
-
}
|
|
56
|
-
|
|
57
|
-
const nodeName = node._name || '(unnamed)';
|
|
58
|
-
const nodePath = parentPath ? `${parentPath}/${nodeName}` : nodeName;
|
|
59
|
-
|
|
60
|
-
indexMap[nodeIndex] = {
|
|
61
|
-
_id: nodeId,
|
|
62
|
-
name: nodeName,
|
|
63
|
-
path: nodePath,
|
|
64
|
-
type: node.__type__
|
|
65
|
-
};
|
|
66
|
-
|
|
67
|
-
if (node._children) {
|
|
68
|
-
node._children.forEach(childRef => {
|
|
69
|
-
traverse(childRef.__id__, nodePath);
|
|
70
|
-
});
|
|
71
|
-
}
|
|
72
|
-
}
|
|
73
|
-
|
|
74
|
-
traverse(1);
|
|
75
|
-
|
|
76
|
-
return { idMap, indexMap, prefab };
|
|
77
|
-
}
|
|
78
|
-
|
|
79
|
-
/**
|
|
80
|
-
* 查找节点索引
|
|
81
|
-
*/
|
|
82
|
-
function findNodeIndex(data, indexMap, nodeRef) {
|
|
83
|
-
if (/^\d+$/.test(nodeRef)) {
|
|
84
|
-
return parseInt(nodeRef);
|
|
85
|
-
}
|
|
86
|
-
|
|
87
|
-
for (const [idx, info] of Object.entries(indexMap)) {
|
|
88
|
-
if (info.name === nodeRef || info.path === nodeRef || info.path.endsWith('/' + nodeRef)) {
|
|
89
|
-
return parseInt(idx);
|
|
90
|
-
}
|
|
91
|
-
}
|
|
92
|
-
|
|
93
|
-
return null;
|
|
94
|
-
}
|
|
95
|
-
|
|
96
|
-
/**
|
|
97
|
-
* 重建所有 __id__ 引用
|
|
98
|
-
*/
|
|
99
|
-
function rebuildReferences(data, deletedIndices) {
|
|
100
|
-
const indexMap = {};
|
|
101
|
-
let newIndex = 0;
|
|
102
|
-
for (let oldIndex = 0; oldIndex < data.length; oldIndex++) {
|
|
103
|
-
if (!deletedIndices.has(oldIndex)) {
|
|
104
|
-
indexMap[oldIndex] = newIndex;
|
|
105
|
-
newIndex++;
|
|
106
|
-
}
|
|
107
|
-
}
|
|
108
|
-
|
|
109
|
-
function updateRef(obj) {
|
|
110
|
-
if (!obj || typeof obj !== 'object') return;
|
|
111
|
-
|
|
112
|
-
if (obj.__id__ !== undefined) {
|
|
113
|
-
const oldId = obj.__id__;
|
|
114
|
-
if (indexMap[oldId] !== undefined) {
|
|
115
|
-
obj.__id__ = indexMap[oldId];
|
|
116
|
-
}
|
|
117
|
-
} else {
|
|
118
|
-
for (const key of Object.keys(obj)) {
|
|
119
|
-
updateRef(obj[key]);
|
|
120
|
-
}
|
|
121
|
-
}
|
|
122
|
-
}
|
|
123
|
-
|
|
124
|
-
for (const item of data) {
|
|
125
|
-
updateRef(item);
|
|
126
|
-
}
|
|
127
|
-
|
|
128
|
-
return indexMap;
|
|
129
|
-
}
|
|
130
|
-
|
|
131
|
-
/**
|
|
132
|
-
* 检查 CLI Helper 插件状态
|
|
133
|
-
*/
|
|
134
|
-
function checkPluginStatus() {
|
|
135
|
-
const http = require('http');
|
|
136
|
-
|
|
137
|
-
return new Promise((resolve) => {
|
|
138
|
-
const req = http.request({
|
|
139
|
-
hostname: 'localhost',
|
|
140
|
-
port: 7455,
|
|
141
|
-
path: '/status',
|
|
142
|
-
method: 'GET'
|
|
143
|
-
}, (res) => {
|
|
144
|
-
let data = '';
|
|
145
|
-
res.on('data', chunk => data += chunk);
|
|
146
|
-
res.on('end', () => {
|
|
147
|
-
try {
|
|
148
|
-
resolve(JSON.parse(data));
|
|
149
|
-
} catch (e) {
|
|
150
|
-
resolve(null);
|
|
151
|
-
}
|
|
152
|
-
});
|
|
153
|
-
});
|
|
154
|
-
|
|
155
|
-
req.on('error', () => resolve(null));
|
|
156
|
-
req.setTimeout(3000, () => { req.destroy(); resolve(null); });
|
|
157
|
-
req.end();
|
|
158
|
-
});
|
|
159
|
-
}
|
|
160
|
-
|
|
161
|
-
/**
|
|
162
|
-
* 触发编辑器刷新
|
|
163
|
-
*/
|
|
164
|
-
function refreshEditor(scenePath) {
|
|
165
|
-
if (!scenePath) return;
|
|
166
|
-
|
|
167
|
-
const http = require('http');
|
|
168
|
-
|
|
169
|
-
const assetsPath = path.dirname(scenePath);
|
|
170
|
-
const projectPath = path.dirname(assetsPath);
|
|
171
|
-
const relativePath = path.relative(projectPath, scenePath).replace(/\\/g, '/');
|
|
172
|
-
const targetSceneUrl = 'db://' + relativePath.replace(/^assets\//, 'assets/');
|
|
173
|
-
|
|
174
|
-
const getCurrentScene = () => {
|
|
175
|
-
return new Promise((resolve) => {
|
|
176
|
-
const req = http.request({
|
|
177
|
-
hostname: 'localhost',
|
|
178
|
-
port: 7455,
|
|
179
|
-
path: '/current-scene',
|
|
180
|
-
method: 'GET'
|
|
181
|
-
}, (res) => {
|
|
182
|
-
let data = '';
|
|
183
|
-
res.on('data', chunk => data += chunk);
|
|
184
|
-
res.on('end', () => {
|
|
185
|
-
try {
|
|
186
|
-
resolve(JSON.parse(data).sceneUrl || null);
|
|
187
|
-
} catch (e) {
|
|
188
|
-
resolve(null);
|
|
189
|
-
}
|
|
190
|
-
});
|
|
191
|
-
});
|
|
192
|
-
req.on('error', () => resolve(null));
|
|
193
|
-
req.setTimeout(3000, () => { req.destroy(); resolve(null); });
|
|
194
|
-
req.end();
|
|
195
|
-
});
|
|
196
|
-
};
|
|
197
|
-
|
|
198
|
-
const sendRefreshRequest = (sceneUrl) => {
|
|
199
|
-
const postData = sceneUrl ? JSON.stringify({ sceneUrl }) : '';
|
|
200
|
-
const req = http.request({
|
|
201
|
-
hostname: 'localhost',
|
|
202
|
-
port: 7455,
|
|
203
|
-
path: '/refresh',
|
|
204
|
-
method: 'POST',
|
|
205
|
-
headers: {
|
|
206
|
-
'Content-Type': 'application/json',
|
|
207
|
-
'Content-Length': Buffer.byteLength(postData)
|
|
208
|
-
}
|
|
209
|
-
}, () => {});
|
|
210
|
-
req.on('error', () => {});
|
|
211
|
-
if (postData) req.write(postData);
|
|
212
|
-
req.end();
|
|
213
|
-
};
|
|
214
|
-
|
|
215
|
-
getCurrentScene().then(currentSceneUrl => {
|
|
216
|
-
sendRefreshRequest(currentSceneUrl === targetSceneUrl ? targetSceneUrl : null);
|
|
217
|
-
});
|
|
218
|
-
}
|
|
219
|
-
|
|
220
|
-
/**
|
|
221
|
-
* 安装 CLI Helper 插件
|
|
222
|
-
*/
|
|
223
|
-
function installPlugin(scenePath) {
|
|
224
|
-
try {
|
|
225
|
-
const assetsPath = path.dirname(scenePath);
|
|
226
|
-
const projectPath = path.dirname(assetsPath);
|
|
227
|
-
const packagesPath = path.join(projectPath, 'packages');
|
|
228
|
-
const pluginPath = path.join(packagesPath, 'cocos2d-cli-helper');
|
|
229
|
-
|
|
230
|
-
if (fs.existsSync(pluginPath)) return true;
|
|
231
|
-
|
|
232
|
-
if (!fs.existsSync(packagesPath)) {
|
|
233
|
-
fs.mkdirSync(packagesPath, { recursive: true });
|
|
234
|
-
}
|
|
235
|
-
|
|
236
|
-
const cliPluginPath = path.join(__dirname, '..', '..', 'editor-plugin');
|
|
237
|
-
|
|
238
|
-
if (!fs.existsSync(cliPluginPath)) return false;
|
|
239
|
-
|
|
240
|
-
fs.cpSync(cliPluginPath, pluginPath, { recursive: true });
|
|
241
|
-
return true;
|
|
242
|
-
} catch (e) {
|
|
243
|
-
return false;
|
|
244
|
-
}
|
|
245
|
-
}
|
|
246
|
-
|
|
247
|
-
/**
|
|
248
|
-
* 加载脚本映射
|
|
249
|
-
*/
|
|
250
|
-
function loadScriptMap(scenePath) {
|
|
251
|
-
const projectPath = path.dirname(path.dirname(scenePath));
|
|
252
|
-
const mapPath = path.join(projectPath, 'data', 'script_map.json');
|
|
253
|
-
try {
|
|
254
|
-
if (fs.existsSync(mapPath)) {
|
|
255
|
-
return JSON.parse(fs.readFileSync(mapPath, 'utf-8'));
|
|
256
|
-
}
|
|
257
|
-
} catch (e) {}
|
|
258
|
-
return {};
|
|
259
|
-
}
|
|
260
|
-
|
|
261
|
-
/**
|
|
262
|
-
* 生成 fileId(用于 PrefabInfo)
|
|
263
|
-
*/
|
|
264
|
-
function generateFileId() {
|
|
265
|
-
const chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/';
|
|
266
|
-
let result = '';
|
|
267
|
-
for (let i = 0; i < 22; i++) {
|
|
268
|
-
result += chars.charAt(Math.floor(Math.random() * chars.length));
|
|
269
|
-
}
|
|
270
|
-
return result;
|
|
271
|
-
}
|
|
272
|
-
|
|
273
|
-
/**
|
|
274
|
-
* 获取预制体根节点索引
|
|
275
|
-
*/
|
|
276
|
-
function getPrefabRootIndex(data) {
|
|
277
|
-
if (!isPrefab(data)) return null;
|
|
278
|
-
return 1;
|
|
279
|
-
}
|
|
280
|
-
|
|
281
|
-
/**
|
|
282
|
-
* 生成 UUID
|
|
283
|
-
*/
|
|
284
|
-
function generateUUID() {
|
|
285
|
-
return crypto.randomUUID();
|
|
286
|
-
}
|
|
287
|
-
|
|
288
|
-
/**
|
|
289
|
-
* 生成预制体的 meta 对象
|
|
290
|
-
* @param {string} uuid - 可选的 UUID,不传则自动生成
|
|
291
|
-
* @returns {object}
|
|
292
|
-
*/
|
|
293
|
-
function createPrefabMeta(uuid) {
|
|
294
|
-
return {
|
|
295
|
-
ver: '1.3.2',
|
|
296
|
-
uuid: uuid || generateUUID(),
|
|
297
|
-
importer: 'prefab',
|
|
298
|
-
optimizationPolicy: 'AUTO',
|
|
299
|
-
asyncLoadAssets: false,
|
|
300
|
-
readonly: false,
|
|
301
|
-
subMetas: {}
|
|
302
|
-
};
|
|
303
|
-
}
|
|
304
|
-
|
|
305
|
-
/**
|
|
306
|
-
* 生成场景的 meta 对象
|
|
307
|
-
* @param {string} uuid - 可选的 UUID,不传则自动生成
|
|
308
|
-
* @returns {object}
|
|
309
|
-
*/
|
|
310
|
-
function createSceneMeta(uuid) {
|
|
311
|
-
return {
|
|
312
|
-
ver: '1.3.2',
|
|
313
|
-
uuid: uuid || generateUUID(),
|
|
314
|
-
importer: 'scene',
|
|
315
|
-
asyncLoadAssets: false,
|
|
316
|
-
autoReleaseAssets: false,
|
|
317
|
-
subMetas: {}
|
|
318
|
-
};
|
|
319
|
-
}
|
|
320
|
-
|
|
321
|
-
/**
|
|
322
|
-
* 保存 meta 文件
|
|
323
|
-
* @param {string} filePath - 资源文件路径(.prefab 或 .fire)
|
|
324
|
-
* @param {object} meta - meta 对象
|
|
325
|
-
*/
|
|
326
|
-
function saveMetaFile(filePath, meta) {
|
|
327
|
-
const metaPath = filePath + '.meta';
|
|
328
|
-
fs.writeFileSync(metaPath, JSON.stringify(meta, null, 2), 'utf8');
|
|
329
|
-
return metaPath;
|
|
330
|
-
}
|
|
331
|
-
|
|
332
|
-
/**
|
|
333
|
-
* 加载 meta 文件
|
|
334
|
-
* @param {string} filePath - 资源文件路径
|
|
335
|
-
* @returns {object|null}
|
|
336
|
-
*/
|
|
337
|
-
function loadMetaFile(filePath) {
|
|
338
|
-
const metaPath = filePath + '.meta';
|
|
339
|
-
try {
|
|
340
|
-
if (fs.existsSync(metaPath)) {
|
|
341
|
-
return JSON.parse(fs.readFileSync(metaPath, 'utf8'));
|
|
342
|
-
}
|
|
343
|
-
} catch (e) {}
|
|
344
|
-
return null;
|
|
345
|
-
}
|
|
346
|
-
|
|
347
|
-
module.exports = {
|
|
348
|
-
// 文件操作
|
|
349
|
-
loadScene,
|
|
350
|
-
saveScene,
|
|
351
|
-
isPrefab,
|
|
352
|
-
|
|
353
|
-
// 索引映射
|
|
354
|
-
buildMaps,
|
|
355
|
-
findNodeIndex,
|
|
356
|
-
rebuildReferences,
|
|
357
|
-
|
|
358
|
-
// 编辑器交互
|
|
359
|
-
refreshEditor,
|
|
360
|
-
installPlugin,
|
|
361
|
-
checkPluginStatus,
|
|
362
|
-
|
|
363
|
-
// Meta 文件管理
|
|
364
|
-
generateUUID,
|
|
365
|
-
createPrefabMeta,
|
|
366
|
-
createSceneMeta,
|
|
367
|
-
saveMetaFile,
|
|
368
|
-
loadMetaFile,
|
|
369
|
-
|
|
370
|
-
// 工具函数
|
|
371
|
-
loadScriptMap,
|
|
372
|
-
generateFileId,
|
|
373
|
-
getPrefabRootIndex
|
|
374
|
-
};
|
package/src/lib/json-parser.js
DELETED
|
@@ -1,185 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* JSON 解析器
|
|
3
|
-
* 将简化JSON转换为CCNode对象树
|
|
4
|
-
*/
|
|
5
|
-
|
|
6
|
-
const { CCNode, CCCanvas, CCWidget, CCSprite, CCLabel, CCButton, CCCamera, CCRichText } = require('./cc');
|
|
7
|
-
const { parseColor } = require('./utils');
|
|
8
|
-
|
|
9
|
-
/**
|
|
10
|
-
* 创建组件实例
|
|
11
|
-
*/
|
|
12
|
-
function createComponent(type) {
|
|
13
|
-
switch (type.toLowerCase()) {
|
|
14
|
-
case 'canvas': return new CCCanvas();
|
|
15
|
-
case 'widget': return new CCWidget();
|
|
16
|
-
case 'sprite': return new CCSprite();
|
|
17
|
-
case 'label': return new CCLabel();
|
|
18
|
-
case 'button': return new CCButton();
|
|
19
|
-
case 'camera': return new CCCamera();
|
|
20
|
-
case 'richtext': return new CCRichText();
|
|
21
|
-
default: return null;
|
|
22
|
-
}
|
|
23
|
-
}
|
|
24
|
-
|
|
25
|
-
/**
|
|
26
|
-
* 解析组件定义
|
|
27
|
-
*/
|
|
28
|
-
function parseComponent(compDef) {
|
|
29
|
-
if (typeof compDef === 'string') {
|
|
30
|
-
return { type: compDef, props: {} };
|
|
31
|
-
}
|
|
32
|
-
if (typeof compDef === 'object' && compDef.type) {
|
|
33
|
-
const props = { ...compDef };
|
|
34
|
-
delete props.type;
|
|
35
|
-
return { type: compDef.type, props };
|
|
36
|
-
}
|
|
37
|
-
return null;
|
|
38
|
-
}
|
|
39
|
-
|
|
40
|
-
/**
|
|
41
|
-
* 应用组件属性
|
|
42
|
-
*/
|
|
43
|
-
function applyComponentProps(comp, props, node) {
|
|
44
|
-
if (!props) return;
|
|
45
|
-
|
|
46
|
-
for (const [key, value] of Object.entries(props)) {
|
|
47
|
-
switch (key) {
|
|
48
|
-
case 'string':
|
|
49
|
-
if (comp._string !== undefined) {
|
|
50
|
-
comp._string = value;
|
|
51
|
-
if (comp._N$string !== undefined) comp._N$string = value;
|
|
52
|
-
}
|
|
53
|
-
break;
|
|
54
|
-
case 'fontSize':
|
|
55
|
-
if (comp._fontSize !== undefined) comp._fontSize = value;
|
|
56
|
-
break;
|
|
57
|
-
case 'lineHeight':
|
|
58
|
-
if (comp._lineHeight !== undefined) comp._lineHeight = value;
|
|
59
|
-
break;
|
|
60
|
-
case 'sizeMode':
|
|
61
|
-
if (comp._sizeMode !== undefined) comp._sizeMode = value;
|
|
62
|
-
break;
|
|
63
|
-
case 'horizontalAlign':
|
|
64
|
-
// 支持语义化字符串:left / center / right
|
|
65
|
-
if (comp._N$horizontalAlign !== undefined) {
|
|
66
|
-
comp._N$horizontalAlign = CCLabel.parseHAlign(value);
|
|
67
|
-
} else if (comp._horizontalAlign !== undefined) {
|
|
68
|
-
comp._horizontalAlign = CCLabel.parseHAlign(value);
|
|
69
|
-
}
|
|
70
|
-
break;
|
|
71
|
-
case 'verticalAlign':
|
|
72
|
-
// 支持语义化字符串:top / center / bottom
|
|
73
|
-
if (comp._N$verticalAlign !== undefined) {
|
|
74
|
-
comp._N$verticalAlign = CCLabel.parseVAlign(value);
|
|
75
|
-
} else if (comp._verticalAlign !== undefined) {
|
|
76
|
-
comp._verticalAlign = CCLabel.parseVAlign(value);
|
|
77
|
-
}
|
|
78
|
-
break;
|
|
79
|
-
case 'color':
|
|
80
|
-
// 兼容写法:组件内的 color 同步到节点颜色
|
|
81
|
-
// (Cocos 中文字/富文本颜色本质是节点颜色,不是组件属性)
|
|
82
|
-
if (node) {
|
|
83
|
-
const parsed = parseColor(value);
|
|
84
|
-
if (parsed && node._color) {
|
|
85
|
-
node._color.r = parsed.r;
|
|
86
|
-
node._color.g = parsed.g;
|
|
87
|
-
node._color.b = parsed.b;
|
|
88
|
-
node._color.a = parsed.a;
|
|
89
|
-
}
|
|
90
|
-
}
|
|
91
|
-
break;
|
|
92
|
-
default:
|
|
93
|
-
if (comp[key] !== undefined) {
|
|
94
|
-
comp[key] = value;
|
|
95
|
-
}
|
|
96
|
-
}
|
|
97
|
-
}
|
|
98
|
-
}
|
|
99
|
-
|
|
100
|
-
/**
|
|
101
|
-
* 应用属性到节点
|
|
102
|
-
*/
|
|
103
|
-
function applyNodeProps(node, def) {
|
|
104
|
-
if (def.name) node._name = def.name;
|
|
105
|
-
if (def.active !== undefined) node._active = def.active;
|
|
106
|
-
if (def.opacity !== undefined) node._opacity = def.opacity;
|
|
107
|
-
if (def.width !== undefined) node._contentSize.width = def.width;
|
|
108
|
-
if (def.height !== undefined) node._contentSize.height = def.height;
|
|
109
|
-
if (def.x !== undefined) node._trs.array[0] = def.x;
|
|
110
|
-
if (def.y !== undefined) node._trs.array[1] = def.y;
|
|
111
|
-
if (def.rotation !== undefined) {
|
|
112
|
-
node._trs.array[5] = def.rotation * Math.PI / 180;
|
|
113
|
-
node._eulerAngles.z = def.rotation;
|
|
114
|
-
}
|
|
115
|
-
if (def.scaleX !== undefined) node._trs.array[7] = def.scaleX;
|
|
116
|
-
if (def.scaleY !== undefined) node._trs.array[8] = def.scaleY;
|
|
117
|
-
if (def.anchorX !== undefined) node._anchorPoint.x = def.anchorX;
|
|
118
|
-
if (def.anchorY !== undefined) node._anchorPoint.y = def.anchorY;
|
|
119
|
-
if (def.color) {
|
|
120
|
-
const parsed = parseColor(def.color);
|
|
121
|
-
if (parsed) {
|
|
122
|
-
node._color.set(parsed.r, parsed.g, parsed.b, parsed.a);
|
|
123
|
-
}
|
|
124
|
-
}
|
|
125
|
-
}
|
|
126
|
-
|
|
127
|
-
/**
|
|
128
|
-
* 解析节点定义(递归)
|
|
129
|
-
* @param {Object} def - 节点定义
|
|
130
|
-
* @returns {CCNode}
|
|
131
|
-
*/
|
|
132
|
-
function parseNode(def) {
|
|
133
|
-
const node = new CCNode(def.name || 'Node');
|
|
134
|
-
|
|
135
|
-
// 应用属性
|
|
136
|
-
applyNodeProps(node, def);
|
|
137
|
-
|
|
138
|
-
// 添加组件
|
|
139
|
-
if (def.components && def.components.length > 0) {
|
|
140
|
-
node._components = [];
|
|
141
|
-
for (const compDef of def.components) {
|
|
142
|
-
const parsed = parseComponent(compDef);
|
|
143
|
-
if (parsed) {
|
|
144
|
-
const comp = createComponent(parsed.type);
|
|
145
|
-
if (comp) {
|
|
146
|
-
applyComponentProps(comp, parsed.props, node);
|
|
147
|
-
comp.node = node;
|
|
148
|
-
node._components.push(comp);
|
|
149
|
-
}
|
|
150
|
-
}
|
|
151
|
-
}
|
|
152
|
-
}
|
|
153
|
-
|
|
154
|
-
// 递归处理子节点
|
|
155
|
-
if (def.children && def.children.length > 0) {
|
|
156
|
-
node._children = [];
|
|
157
|
-
for (const childDef of def.children) {
|
|
158
|
-
const child = parseNode(childDef);
|
|
159
|
-
child._parent = node;
|
|
160
|
-
node._children.push(child);
|
|
161
|
-
}
|
|
162
|
-
}
|
|
163
|
-
|
|
164
|
-
return node;
|
|
165
|
-
}
|
|
166
|
-
|
|
167
|
-
/**
|
|
168
|
-
* 从简化JSON解析为CCNode树
|
|
169
|
-
* @param {Object|string} json - JSON对象或字符串
|
|
170
|
-
* @returns {CCNode}
|
|
171
|
-
*/
|
|
172
|
-
function fromJSON(json) {
|
|
173
|
-
if (typeof json === 'string') {
|
|
174
|
-
json = JSON.parse(json.replace(/^\uFEFF/, '').trim());
|
|
175
|
-
}
|
|
176
|
-
|
|
177
|
-
const rootDef = Array.isArray(json) ? json[0] : json;
|
|
178
|
-
return parseNode(rootDef);
|
|
179
|
-
}
|
|
180
|
-
|
|
181
|
-
module.exports = {
|
|
182
|
-
fromJSON,
|
|
183
|
-
parseNode,
|
|
184
|
-
applyNodeProps
|
|
185
|
-
};
|