FairyGUI-egret 优化ui资源加载

背景:egret重度游戏项目,ui资源都比较大,加载较慢,翻翻加载ui的源码看一下有没有优化空间:

https://github.com/fairygui/FairyGUI-egret/blob/master/source/src/UIPackage.ts

public static async loadPackage(resKey: string): Promise<UIPackage> {
            return new Promise<UIPackage>(async resolve => {
                let pkg: UIPackage = UIPackage._instById[resKey];
                if (pkg) {
                    resolve(pkg);
                    return;
                }

                const asset = await RES.getResAsync(getAssetResKey(resKey, "fui"));
                pkg = new UIPackage();
                pkg._resKey = resKey;
                pkg.loadPackage(new ByteBuffer(asset));
                let cnt: number = pkg._items.length;
                let tasks = [];
                for (var i: number = 0; i < cnt; i++) {
                    var pi: PackageItem = pkg._items[i];
                    if (pi.type == PackageItemType.Atlas || pi.type == PackageItemType.Sound) {
                        tasks.push(RES.getResAsync(pi.file));
                    }
                }

                if (tasks.length > 0)
                    await Promise.all(tasks);

                UIPackage._instById[pkg.id] = pkg;
                UIPackage._instByName[pkg.name] = pkg;
                UIPackage._instById[pkg._resKey] = pkg;

                resolve(pkg);
            });
        }

可以看到代码里是先加载 .fui 的配置资源,等到它加载完成后,从其中解析出需要的 atlas\sound 资源,然后等待所有的资源加载,ui加载完成。而egret在运行会通过 assetsManager 加载全量资源的映射表,我们可以在此时建 收集每个fgui包的全部资源(即 .fgui配置 和 atlas\sound 资源),这样在loadPackage 时直接并行加载单个ui包的全部资源,理论上单个包的加载速度可以提升近一倍。

具体代码修改如下:

注意:代码是基于我这边内部版本修改,行数可能对不上,具体修改要参考一下上下文的scope。
修改后执行 ./tools/bin/egret build 编译js。

egret - assetsmanager:

src/extension/assetsmanager/src/core/FileSystem.ts

    export interface FileSystem {
 		...

+++++++++++++++++++++>>>>>> line 44

        collectFguiPkgAtlasAndSound(pkg:string, name:string):void;

        getFguiPkgAtlasAndSounds(pkg:string): string[];
  <<<<<<+++++++++++++++++++++  
}

src/extension/assetsmanager/src/core/ResourceConfig.ts

export class ResourceConfig {
 ...
 
+++++++++++++++++++++>>>>>> line 265
        public getFguiPkgItems(pkgName:string): string[] {
            return config.config.fileSystem.getFguiPkgAtlasAndSounds(pkgName);
        }
<<<<<<+++++++++++++++++++++      

 ...
}

src/extension/assetsmanager/src/processor/Processor.ts

                if (!fileSystem) {
                    fileSystem = {
                    	...
                    	
 +++++++++++++++++++++>>>>>> line 639
                        },

                        fguiPkgAtlasAndSound: {},
                        collectFguiPkgAtlasAndSound:(pkgName:string, name:string)=>{
                            let temp:string[] = fguiPkgAtlasAndSound[pkgName];
                            if (!temp) {
                                temp = [];
                                fguiPkgAtlasAndSound[pkgName] = temp;
                            }
                            temp.push(name);
                        },
                        getFguiPkgAtlasAndSounds:(pkgName:string)=>{
                            return fguiPkgAtlasAndSound[pkgName];
<<<<<<+++++++++++++++++++++

						...
					}

+++++++++++++++++++++>>>>>> line 667
                let fguiPkgAtlasAndSound: {[index:string]:string[]} = fileSystem['fguiPkgAtlasAndSound'];
<<<<<<+++++++++++++++++++++
		        for (let resource of data.resources) {
		
					...
+++++++++++++++++++++>>>>>> line 678
					//fgui 资源
                    if (resource.url.substring(0,10) == "assets/ui/") {
                        let subfix = resource.url.substring(10+resource.name.length)
                        switch(subfix) {
                            case ".fui":
                                fileSystem.collectFguiPkgAtlasAndSound(resource.name, resource.name);
                                break;
                            case ".mp3":
                                let idx_ = resource.name.lastIndexOf('_');
                                fileSystem.collectFguiPkgAtlasAndSound(resource.name.substring(0,idx_), resource.name);
                                break
                            case ".jpg":
                            case ".png":
                                let idx_atlas = resource.name.lastIndexOf('_atlas');
                                fileSystem.collectFguiPkgAtlasAndSound(resource.name.substring(0,idx_atlas), resource.name);
                                break;
                            default:
                                console.warn("unparsered fgui resource :" + resource.url);
                        }
                    }
<<<<<<+++++++++++++++++++++
                }
+++++++++++++++++++++>>>>>> line 702
                for(let key in fguiPkgAtlasAndSound) {
                    let temp:string[] = fguiPkgAtlasAndSound[key];
                    temp.sort(); //排序后第一个应为 .fui文件
                 }
<<<<<<+++++++++++++++++++++

src/extension/assetsmanager/src/shim/Resource.ts

module RES {
	...
+++++++++++++++++++++>>>>>> line 320
	export function getFguiPkgItems(pkgName: string): string[] {
	        return instance.getFguiPkgItems(pkgName);
	    }

<<<<<<+++++++++++++++++++++

		...

	export class ResourceConfig {
    	...
    	
+++++++++++++++++++++>>>>>> line 829
        /**
         * 获取配置文件中 fugi 包的资源名合集
         * @method RES.getFguiPkgItems
         * @param pkgName {string} 包名
         * @returns {string[]}
        */
        @checkNull
        public getFguiPkgItems(pkgName:string): string[] {
            return config.getFguiPkgItems(pkgName);
        }
<<<<<<+++++++++++++++++++++
 		...
 		
}

FairyGUI

src/UIPackage.ts

public static async loadPackage(resKey: string): Promise<UIPackage> {
		...
		
		let keys = RES.getFguiPkgItems(resKey);
		for(let key of keys) {
		    tasks.push(RES.getResAsync(key))
		}
		
		let assets = await Promise.all(tasks);
		
		pkg = new UIPackage();
		pkg._resKey = resKey;
		pkg.loadPackage(new ByteBuffer(assets[0]));

		...
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值