Attention | Topic was automatically imported from the old Question2Answer platform. | |
Asked By | Lorèloi |
I am looking for a way to make a RigidBody2D stick on the “surface” of a moving KinematicBody2D as soon as it collides it. Once sticked, it would follow the movement of the moving collider as if it were part of it, ignoring gravity and other forces. I guess it boils down to find a way to apply one object’s transform to another.
In my test scene, the RigidBody2D is called stickingBall
. The KinematicBody2D, called colliderRotatingDisc
, simply rotates. The first falls on the latter. This image shows my scene setup:
Ideally, I would like the solution to work whatever the movement of the collider is, and not only simple rotations. (That’s why I didn’t want to apply the collided object velocity (body_state.get_contact_collider_velocity_at_position()
) on a circular path.)
So far I have tried two lines of research:
- Detach the root node of StickingBall from the scene tree and attach it as a child of colliderRotatingDisc, using the same global position and rotation. This way, Sticking ball indeed follows the movement of colliderRotatingDisc. However, in my actual game, StickingBall has a Camera2D, and this operation makes the camera shake nastily. In addition, this method seems unpractical and quite savage to me. ^^’
- Change the transform matrice of StickingBall, trying one way or another to apply the transform of the object it collides. There is obviously something I don’t understand with them, as I didn’t achieve the desired result,
My scripts :
Script of the StickingBall :
(For now, it just activates the custom integrator and stops the ball when the ball collides.)
extends RigidBody2D
var is_sticking = false
func _ready():
# Enable the logging of 5 collisions.
set_contact_monitor(true)
set_max_contacts_reported(5)
# Apply Godot physics at first
set_use_custom_integrator(false)
func _integrate_forces( body_state ):
if body_state.get_contact_count() > 0 :
is_sticking = true
# Ignore Godot physics once the ball sticks
set_use_custom_integrator(true)
if is_sticking :
# TODO: Instead of immobilizing the ball, I would like to make it "stick" to the rigidbody it collides.
body_state.set_linear_velocity( Vector2(0,0) )
body_state.set_angular_velocity( 0 )
Script of the colliderRotatingDisc :
extends Node2D
export var rot_speed = PI / 4 # rad/sec
func _ready():
set_process(true)
func _process(delta):
get_node("KinematicBody2D").rotate(rot_speed * delta)