+3 votes

Why doesn't disable the Collisionshape2d in code: "$CollisionShape2D.disabled=true". The collision shape is attached to a KinematicBody2. I did it exactly as shown in a tutorial, except that in tutorial Godot 3.0 was used.

in Engine by (30 points)

5 Answers

+1 vote

For some reason the following code doesnt work:

$CollisionShape2D.disabled = true

, however using the following works perfectly:

get_node("CollisionShape2D").disabled= true

you can also visualize the collisions from the Debug -> Visible Collision Shapes .. when it's disabled it turns to grey

I suggest you check in bugs list, and do a bug report if no one reported it earlier and not use $CollisionShape2D.disabled till it's solved

by (298 points)

Thank you for answer but it still doesn't work. It is strange that the collision shape does turn to grey but it is actually not disabled because can't pass through it.

hmm... very weird , do you mind uploading the project file to any storage cloud and share the link so I can check it in my side?

the link is private, cant open it

0 votes

I've encountered the same issue in Godot 3.1.2 and used layers as a workaround, but this seems to be fixed now in Godot 3.2 !

by (14 points)
+14 votes

Try this:

$CollisionShape2D.set_deferred("disabled", true)

Which waits until it's "safe" to actually disable the collision shape.

by (16,712 points)

I had the same issue with my project and calling

$CollisionShape2D.set_deferred("disabled", true)

resolved my enabling/disabling collision shape issue. Thanks

Thank's!!!! You really help me)

It really helps me!

Thank you for this,

The following code just doesn't work and it's the logical and common way to do this.

get_node("CollisionShape2D").disabled= true
$CollisionShape2D.disabled = true

can someone explain why this set_deferred thing works? The reason to disable it just because it's "safe" just doesn't make sense to me

That's because, to my understanding, the physics engine makes calculations for every frame based on collision shapes and other objects. If you suddenly disable a collision shape, it may interfere with the physics engine since it could be using the collision shape at that time. If you instead disable the collision shape when the physics engine is done with the calculations for the current frame using "setdeferred" or "calldeferred", no conflict is going to occur. Thus, we call it "safe" to make such changes when the physics engine is idle. If you don't respect that, you should be getting runtime errors.

Thanks, get_node("StaticBody2D/CollisionShape2D").set_deferred("disabled", false) worked for me :)

+1 vote

Even I am working on the same project. Instead of disabling CollisionShape2D I just deleted it.
It doesn't affect the scene but does the work.

$CollisionShape2D.free() 
by (32 points)

You are a genius!
Thank you so much, I registered the account just to upvote and comment on your post
The other solution was working but I did not understand a word of it. I am just a beginner and I ran into so many problems when I searched for the solutions on google, all of them are like super high level and I couldn't understand anything. Your solution is the easiest to understand, the most efficient and optimized.

Thank you so much Again!

0 votes

you actually can, I had the same problem you need to do:

"$CollisionShape2D.set_disabled(true)"

The "set" part is necessary, a bit confusing, I know.

What I would want to know is if there is any difference in doing it like this or with "set_deferred".

by (14 points)
edited by

This is incorrect. There is no property called set_disabled, so this will produce an error.

You can either do

$CollisionShape2D.disabled = true

or call the setter

$CollisionShape2D.set_disabled(true)

Although the former is standard practice; properties are directly accessible.

It may be you're confused by the need to use set_deferred() when a property of a physics object needs to be changed during the physics processing step. Since that's not allowed, the change must be deferred to the end of physics processing.

set_deferred takes two arguments: the property name, and the new value:

$CollisionShape2D.set_deferred("disabled", true)

Oh, I'm sorry I did meant to write:

"$CollisionShape2D.set_disabled(true)"

I edited my comment to avoid confusion for future readers. That was me typing it wrong as I am using it in my game xD

But I am still not sure of "set_ deferred", is it better to use it than "set_disabled" in general. Or you should choose one or the other depending on if you need it sync to physics or not?

They're the same thing, it's just that you're not allowed to disable collision during the physics step - if you do, you'll get the message that you need to defer it.

Welcome to Godot Engine Q&A, where you can ask questions and receive answers from other members of the community.

Please make sure to read Frequently asked questions and How to use this Q&A? before posting your first questions.
Social login is currently unavailable. If you've previously logged in with a Facebook or GitHub account, use the I forgot my password link in the login box to set a password for your account. If you still can't access your account, send an email to [email protected] with your username.