+2 votes

I'm trying to create a dynamic (that is, through a gdscript) rigidbody, including sprite and collider. The Rigidbody and the geometry works fine, but I have trouble with the collider.

I have set up a 2d scene like this:
abc

Blue rectangle is a static body, the red box is a normal rigidbody.

I then attach a gdscript to the root node. The script creates a rigidbody, then add it as a child of the scene node. Then it creates a polygon (green triangle), and add it as a child of the rigidbody. Finally it creates a box-shaped-collider, and also makes it a child of the rigidbody.

The code is here:

extends Node2D
var rigidbody
var geometry
var collider

func _ready():
    create_rigidbody()
    create_geometry()
    create_collider()

func create_rigidbody():
    rigidbody = RigidBody2D.new()
    rigidbody.set_gravity_scale(3)
    rigidbody.set_pos(Vector2(100,0))
    add_child(rigidbody)

func create_geometry():
    geometry = Polygon2D.new()
    var points = Vector2Array()
    points.push_back(Vector2(0,0))
    points.push_back(Vector2(50,0))
    points.push_back(Vector2(0,-50))
    geometry.set_polygon(points)
    geometry.set_color(Color(0,1,0,1))
    rigidbody.add_child(geometry)

func create_collider():
    collider = CollisionShape2D.new()
    var shape = RectangleShape2D.new()
    shape.set_extents(Vector2(35,35))
    collider.set_shape(shape)
    collider.set_pos(Vector2(25,-25))
    rigidbody.add_child(collider)

When run (with debug->show colliders turned on), the game shows:
enter image description here

(I made the colliders a bit larger than the geometry, so they are easier to identify)

I can see my code has generated everything as I wanted, and that the rigidbody fall with the triangle and the box-collider.

However, the collider doen't react when hitting the blue static body - it just passes through.

I can't figure out why. Is there a setting or something on the collider I need to check for this to work?
Any help is greatly appreciated.

The scene i made is here:
scene.scn

Thanks in advance.

in Engine by (17 points)
edited by

... and what is your question?

1 Answer

+4 votes
Best answer

CollisionShapes are editor helpers, they likely won't work in runtime. Instead, you should use the CollisionObject2D API (which is inherited by RigidBody2D): http://docs.godotengine.org/en/latest/classes/class_collisionobject2d.html#class-collisionobject2d
So your shape can be added with rigidbody.add_shape(shape, transform) instead of a child node.

by (27,952 points)
selected by

Thank you very much. This really helped - especially the "add_shape"-function.

If other get this problem, I solved it by changing my create_collider() function to:
func create_collider():
var shape = RectangleShape2D.new()
shape.set_extents(Vector2(35,35))
rigidbody.add_shape(shape)

This will not show the collider during debug, and I had to play around with the positioning, but this worked.

In Godot 3 you can add collision shapes directly and it will just work. It looks like this shape owner function does the same as the 2.1 version though, but it's no longer the only way to achieve this now.

Yup - so this is how I'm doing it for my "player" node with a set of points defined like this:

var w = 20
var h = 30
var points = PoolVector2Array([
    Vector2(       0,  0.6666 * h),
    Vector2(-0.5 * w, -0.3333 * h),
    Vector2.ZERO,
    Vector2.ZERO,
    Vector2( 0.5 * w, -0.3333 * h),
    Vector2(       0,  0.6666 * h),
])

Then in my _ready handler, I do:

var shape = ConvexPolygonShape2D.new()
shape.set_points(points)
var ownerId = create_shape_owner(self)
shape_owner_add_shape(ownerId, shape)
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 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 webmaster@godotengine.org with your username.