This site is currently in read-only mode during migration to a new platform.
You cannot post questions, answers or comments, as they would be lost during the migration otherwise.
0 votes


I created a script to place random objects randomly on a map.
I have a function that checks if the player moves over the object and that detects if the object is inside a wall.

Unfortunately I haven't figured out yet how to move the object after the wall collision has been detected.

From the _on_Area2D_body_enter function, how could I tell which item node was colliding with the wall?

Or is it too late at that point?

My code:

extends Sprite

var xwg = 0
var ywg = 0

func _ready():
    # Called every time the node is added to the scene.
    # Initialization here

func place_random_item(nodename, amount, xwidth, ywidth):
    xwg = xwidth
    ywg = ywidth
    var itemnumber
    var itemname
    var iposx = 0
    var iposy = 0
    var iterate = 0

        itemnumber = randi()%4+1
        itemname = str(itemnumber)
        iposx = randi()%int(xwidth)-100
        iposy = randi()%int(ywidth)-100
        var new_item = 
        var new_sprite =
        var new_collision =
        var shape =




        new_item.connect("body_enter", self, "_on_Area2D_body_enter")
        iterate += 1

func _on_Area2D_body_enter( body ):
    if(body.get_name() == "Player"):
    elif(body.get_name() == "Walls"):
        var iposx= randi()%int(xwg)-100
        var iposy= randi()%int(ywg)-100
in Engine by (15 points)
edited by

Why would you detect if it's in a wall? Is this a flaw in your random spawn function?
I think you could do a shape itersection query before you spawn the object.

Also, I see so many people fall into this trap:
var new_collision =
Don't do this from code. It won't work after you export your game. CollisionShape2D is an editor-only class and is unavailable outside of the editor. Use the shape API instead:

I am just placing items at random coordinates on the map, that seemed easiest, but it won't prevent them from being spawned inside the walls. The items can tell me if they are spawned inside a wall though so I thought I could just move them in that event.

The location my items spawn is basically just this:


this then tells me if they are in an inaccessible place:

new_item.connect("body_enter", self, "_on_Area2D_body_enter")
        iterate += 1

func _on_Area2D_body_enter( body ):
    if(body.get_name() == "Player"):
    elif(body.get_name() == "Walls"):
        var iposx= randi()%int(xwg)-100
        var iposy= randi()%int(ywg)-100

The way I have it now all I'd need is a way to change the items position inside the function _on_Area2D_body_enter( body ):
But of course the new_item does not point to the right item at that point.
Is there a way to place items on tiles instead of coordinates and preclude any tiles covered by wall tiles?

Thanks for the tip with CollisionShape2D though!

I'm not sure what are you trying to do, but if it's simple collision, isn't making your player character a kinematicBody2D enough?
Because for what I see, you have a solid setup with collision nodes and shapes, I don't see how your character isn't responding to the collisions, or do you want to make a different kind of interaction and not simple collisions?


No the thing is collisions do work, if my player moves over the item it gets registered. If the item gets spawned inside a wall that also gets registered.

But now I want to tell the engine to move the item that was spawned inside a wall somewhere else.

The notification of a collision works with the function _on_Area2D_body_enter( body ): but unfortunately once I am inside that function I don't see a way to figure out which item called that function. It gets the body of the thing (player, walls) that ran into the item but not which item started the function. The function was made with this:

new_item.connect("body_enter", self, "_on_Area2D_body_enter")

Can I somehow not only transmit the body that ran into the item but also the item that was run into by calling this function?
Am I doing this totally wrong? I guess the shape_intersection Zylann pointed out works in a different way?

1 Answer

+2 votes
Best answer

In order to find wether you can spawn an object before actually spawning it, you can do a shape intersection query to ask the collision engine: "hey, is there anything here if I put this shape?"

To do that you need to use the direct space state 2D.
The doc explains how to use it here for raycasts:

In order to do this with a shape instead of a ray, you can do this (untested):

var space_state = get_world().get_direct_space_state()
var query =
var shape =
var hits = space_state.intersect_shape(query)
if hits.size() != 0:
    print("There is something here!")

The only limitation to this method is that you should execute it inside _fixed_process, because it's the only time where physics are in sync with scripts (your signal is also executed in a deferred way for this reason).

by (29,510 points)
selected by

Thank you, I'll try that out soon!

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.