发现一个可以大幅度优化cocos性能问题的知识点

场景:在一个非常激烈的场面,各个人物会发射特别多子弹,当子弹超过5000(某个数量)时,就会突然卡顿到死,200ms多渲染1帧,原因是因为子弹到达位置会进入节电池,但是进入节点池会setParent(null),之后在_updateSiblingIndex中遍历children,打个比方如果5000单位同时进节点池再下一帧创建,每帧会多循环5000*5000遍,也可能这个问题不是因为_updateSiblingIndex,源码也不是特别熟悉,是在性能分析中一步步分析出来的,问题一定是在setParent中,我修改节点池逻辑让节点UIOpacity透明,修改过后70ms渲染1帧,setParent建议还是设置脏标记来处理,还有setSiblingIndex也建议用脏标记,可以吗官方大佬

空场景,当处理5000空节点时是15ms,当处理10000空节点时50ms,当然正常业务情况肯定要比这个复杂,有其他渲染
private _child: Node[] = [];
private _handleType = 0;

start() {

    for (let i = 0; i < 10000; i++) {

        let node = new Node();

        node.parent = this.node;

        this._child.push(node);

    }

}

update(deltaTime: number) {

    this._handleType++;

    for (const node of this._child) {

        if (this._handleType % 2 === 1) {

            node.parent = null;

        }

        else {

            node.parent = this.node;

        }

    }

}

我之前遇到的情况是挂了碰撞之后会出现这种情况,没有挂自带碰撞或者自己写碰撞的话会好很多

是没有碰撞的

数量级大了肯定也是会卡的,直能建议不要直接设置父节点,你现在的处理方式也是大多数人的处理方式,还有你可以顺便试试加碰撞,那可不是200ms :rofl:

昨天面试了个做捕鱼的公司我和面试官说碰撞在捕鱼里不是大头 (捕鱼的碰撞才多少而且子弹还有上限)大头在插入节点 他不相信我
image
我是这样子做的 :rofl:

1赞

setParent和setAcitve都是性能消耗大户…

是的 在低端机上尤为明显 卡到爆炸 还有spine不开缓存也是~~~

嗯 老问题了, 代价比较小的方式:要么坐标移出屏幕,要么设置透明。 但是要注意父节点释放的时候,处理好内存池。

所有移出屏幕和设置透明哪个比较省性能?

得看底层,如果设置透明度,不会渲染,就省性能。移除屏幕,如果不渲染,也省性能。
但移除到屏幕外,大概率还会渲染。

底层确实不会渲染 我看了有个if == 0 就不渲染的逻辑哈哈

但是移出屏幕和设置透明dc都不会减少,只有setParent和setAcitve会减少,所有还是要看情况使用。

试了一下,用 UIOpacity设置0的话,DC不会减少,用颜色值,直接修改透明度0,可以减少DC。

2赞

1赞