cocos-engine
cocos-engine copied to clipboard
Error when trying to destroy or deactive a node with rigibody and collider with box2D
Cocos Creator version
3.8 beta
System information
Windows 11
Issue description
The game causes an error if I destroy a node in the BEGIN_CONTANT event or update.
Example:
setContactListeners() {
const collider: Collider2D = this.getComponent(Collider2D);
if (collider) {
collider.on(Contact2DType.BEGIN_CONTACT, this.onBeginContact, this);
}
}
onBeginContact(selfCollider: Collider2D, otherCollider: Collider2D, contact: IPhysics2DContact | null) {
console.log("onBeginContact");
this.node.destroy();
}
Relevant error log output
physics-contact.ts:236 Uncaught TypeError: Cannot read properties of null (reading 'enabledContactListener') at PhysicsContact.emit (physics-contact.ts:236:20) at PhysicsContactListener._onPreSolve [as _PreSolve] (physics-world.ts:415:11) at PhysicsContactListener.PreSolve (physics-contact-listener.ts:76:18) at b2PolygonAndCircleContact.Update (box2d.umd.js:11809:24) at b2ContactManager.Collide (box2d.umd.js:12479:17) at b2World.Step (box2d.umd.js:19588:33) at b2PhysicsWorld.step (physics-world.ts:161:21) at PhysicsSystem2D.postUpdate (physics-system.ts:290:31) at Director.tick (director.ts:692:38) at Game._updateCallback (game.ts:1027:22)
Steps to reproduce
Create a node with a collider and a rigibody and destroy the node with it hits another collider in the BEGIN_CONTACT event or update.
Minimal reproduction project
No response
Same problem in CC 3.8.1 Tested with Box2D-wasm Based 2D Physics System. Same problem. I have to destroy the node at the lateUpdate event.
I have the same issue and i cant fix this. Anyone can help us .-. bruhhh
me too
I tried change version to 3.7.1, and fix it by live call instead call by onContact or schedule, and it worked
Could anyone provide a demo? Thanks.
SOLUTION : I have to destroy the node at the lateUpdate event.
private _isDestroyed:boolean = false;
lateUpdate(deltaTime: number) {
if (this._isDestroyed) {
this.node.destroy();
}
}
setContactListeners() {
const collider: Collider2D = this.getComponent(Collider2D);
if (collider) {
collider.on(Contact2DType.BEGIN_CONTACT, this.onBeginContact, this);
}
}
onBeginContact(selfCollider: Collider2D, otherCollider: Collider2D, contact: IPhysics2DContact | null) {
console.log("onBeginContact");
this._isDestroyed = true;
}
Node.destory() will set node's active to false, which will set all components of the node to false too. And set active to false in contact call back will cause exceptions in box2d. So it is the limitation of box2d to setActive to false in contact call back.
i still meet this issue on v3.8.3. @BenoitFreslon 's solution works well but i hope this issue will be fixed officially.