体验地址:Cocos Creator | BabyShark
*资源有25MB 模型较多,请等待下加载。
视频链接:Cocos机型适配方案_哔哩哔哩_bilibili
商店链接:BenchMark性能检测+性能适配 | Cocos Store
*项目所有的3D素材都来自 sketchfab CCC授权
*加载图片来自A站@Bandarai 大佬
为什么要做性能检测
在讨论为什么要做性能检测前,先来看下这个项目的成品。
*超高画质
*中档画质
*低档画质
在高中低3档设置上,手机的画质有了截然不同的表现,随着手机行业的发展,手机的性能越来越高,从2016年的晓龙820到2022 晓龙gen 8, 手机的性能提升了近6倍不止。
*2016年安安兔数据
*2022年安安兔数据
那是不是意味着在 3D赛道,或者在目前Cocos 3.x 主攻的3D小游戏赛道,我们可以做更卷的画质呢?
答案是存在疑问的。
根据Android Studio,安卓机型占比分析,可以看出,2022了,从安卓4.0 到安卓9.0,还有着不小的用户存量。
所以在机型适配上,我们尽量要实现T型适配,针对高端机型,提供高品质高画质内容,针对中低端机型,要向下兼容,确保运行流程。
2.0 Cocos 性能检测
这就有了第一个问题,如何在Cocos 平台上做机型适配。
考虑到目前小游戏平台内存和性能的局限性,首先我们就放弃了实时检测。
其次,目前大部分主流机型的测试报告都可以从https://gfxbench.com 网站上拿到,所以本次的方案,通过对比法,获取手机的FPS跑分报告,并做出相应的适配方案。
第一步 ,通过pipelineSceneData拿到GPU型号
*pipelineSceneData内的信息
第二步 ,用手机的GPU信息,加上手机分辨率的长乘宽的成绩去和gfxbench的数据库进行对比(这里我们使用了第三方的地址https://unpkg.com/browse/detect-gpu@4.0.14/dist/benchmarks/ 的数据缓存,建议把这些json保存在自己的cdn,或者把手机的json信息保存在本地做解析)。
如果拿到了手机的fps跑分信息,通过提前定义好的适配等级(0-4,共5级),来获取手机表现。
第三步 ,如过没有拿到GPU信息,或者gfxbench里匹配的数据样本,我们通过手机的长宽信息进行判定(准确率略低),这个算法主要是基于全屏屏手机屏幕的价位决定的。
到这一步,就拿到了手机的性能评级,最后,我们就可以根据性能评级,去做高低端机型优化啦
3.0 高低端机型优化
Cocos 性能消耗主要分布在
-
渲染开销
-
物理开销
-
逻辑开销
我们要根据手机的性能评级分别去做以上3点的优化。
感谢xzben 的教我阅读源码,通过阅读Cocos源码,可以看到game.frameRate=30 时候,代码层在_updateCallback有做跳帧处理,针对动画和物理的设置物理的线性速度都会有影响, 通过设置frameRate=30 可以很有效的提升低端机性能。
private _updateCallback () {
const director = legacyCC.director;
let callback;
if (!JSB && !RUNTIME_BASED && this._frameRate === 30) {
let skip = true;
callback = (time: number) => {
this._intervalId = window.rAF(this._frameCB);
skip = !skip;
if (skip) {
return;
}
director.tick(this._calculateDT(time));
};
} else {
callback = (time: number) => {
director.tick(this._calculateDT(time));
this._intervalId = window.rAF(this._frameCB);
};
}
this._frameCB = callback;
}
游戏的一大部分逻辑开销经常来自 update 或者 lateUpdate 的消耗,这部分逻辑大佬们可以针对项目做适配。
针对物理开销,如果 frameRate=30后,我们可以对物理的线性速度额外乘2,但对于高速运动的物理场景,可能会出现穿墙都情况。
接下来就是渲染开销,这里贴下代码,大佬们也可以商店直接下载喔。
这里通过全局的宏设置,可以控制大部分渲染相关的参数,包括雾效,阴影,阴影贴图大小,IBL等。
针对渲染开销,这里也做了4层优化
显存开销:阴影贴图大小,天空盒是否开启(如果需要严格控制显存,这里天空盒需要做动态加载,Demo是提前加载好的)
网格渲染开销:网格LOD,阴影是否开启
常规渲染开销:IBL,雾效,普通材质与高级材质切换等
粒子特效开销:粒子特效剔除,粒子特效粒子数量减少
我们首先对比下 超高和高 的优化(右边是超高)
超高使用了IBL,使用PBR材质的有受环境光影响,同时阴影贴图大小设置为了1024,阴影的细节会更细腻。
再对比高和中 ,左边中档关闭了阴影,整个画面的立体感下降了不少,老美人鱼显得更加沧桑,同时frameRate 设置成了30,乌鸦和虎鲸的动画会有一点生硬。
最后是中和低。
低档我们把水面替换成了Unlit无光照材质,同时暂停了粒子特效模拟的God Ray,画面的层次和细节又少了一点点。
最后我们看下低档的全局效果,背后的4根封印石柱设置了LOD Mesh,相比中档,减少了55000左右的三角形个数,但是在视觉上的差异却不大,这里的LOD并没有做视距上的控制(to-do)
LOD Mesh 对比(右边为低档)
这里创建LOD Mesh也比较简单,复制一份Mesh,直接通过自带的Mesh压缩即可。
实际应用场景的中,通常会把复杂Mesh,根据离摄像头的距离或者适配的方案的设置,做LOD的降级,如下图的树,最低档的LOD开销只有最高档的三分一不到。
LOD方案在草面设置就更暴力一点,近处的是几何体,中景用的面片插片,到了远景直接用一个面片躺平了。
最低档就不多介绍了,大佬们可以看下关闭了FOG 雾效的Demo效果。
4.0 to-do
*增加 延迟渲染管线 Demo,实现分辨率修改+FXAA等级适配
*基于摄像机距离的LOD 实现
*更优的材质适配方案
*粒子数量适配
5.0 FAQ
Q1 : 部分手机浏览器上分辨率数据不准?
A: 以三星S21为例,使用数据库没用的adreno 660 GPU,这时候请求了分辨率判断,三星在省电模式下,分辨率会改为720P,这时候判定就会失误。
Q2: UNPKG - detect-gpu 里的JSON数据体积很大,会不会影响加载
A :这里只会下载对应的GPU数据,对速度和域名有要求的项目(比如微信),可以把这些CDN加载本地,对于统计到没有GPU,可以下载benchmark跑分后加入到JSON当中。
部分对加载速度要求很严的项目,也可以把这部分逻辑上传到服务器,前端只负责获取GPU和分辨率信息。
Q3: 检测出来的GPU信息好长,没有正确返回。
A:这个Benmark信息是外网的,弱网环境下可能会请求不到,建议放在自己的CDN或者本地喔。
6.0 商店链接
商店已上线,Support me 一点点 奶茶
商店链接:BenchMark性能检测+性能适配 | Cocos Store