0 votes

Hello. In my top down 2D project when I create logs that player can shift(something like in Zelda 2D), I make Gravity Scale to 0. In order for gravity to "pull" the log to the surface, as if along the Z axis, which is not in Rigidbody2D. That is, when I set the GravityScale to 0 so that the log does not roll from top to bottom across the screen, it turns out that with this parameter, the mass and weight do not affect anything and the log is in zero gravity. Therefore, I had a question, how to make the gravity of Rigidbody2D work in the TopDown project?

Godot version 3.3
in Engine by (38 points)

2 Answers

+1 vote
Best answer

Your halfway there with the zero g but you'll need to code in thr friction of the "floor" yourself.

Friction is a force proportional to velocity and in the opposite direction, the scale depends if the log is on ice low friction or mud high friction.

EDIT: see an example implentation below:

by (104 points)
edited by

Thank you. I will try to find a way to do this

Sorry for second question. But could you suggest me how to make this (if you know) please. Because I just haven't really figured out Godot yet, and how to do things like that

Add this script to your rigid body, it would be even simplier but addcentralforce() behaves in an unusual manner and previous forces need clearing on the next frame. This acts like the damper (I just came across) but in your own script you could tweak the friction depending on what your object is on top of:

 extends RigidBody2D

export(float) var mu_static = 0.8  # friction coefficients
export(float) var mu_moving = 0.5  # pushing something moving is easier
# mu depends on what material the object is on, so use area detectors and change
# this values depending on ice or mud

export(float) var move_strength = 50

var applied_forces: Vector2 = Vector2(0, 0)

func add_force_for_frame(force: Vector2):
    # add_force adds a permanent force, for a temporary one we need to wipe it
    # by undo the force next frame, just keep track of forces applied
    applied_forces += force
    self.add_central_force(force)

func _ready() -> void:
    # no world gravity pushing the object down (in the +y) direction
    # we are top down so gravity is acting into the screen (in +z) but the
    # "ground" normal force is canceling it out
    self.gravity_scale = 0

func _physics_process(delta: float) -> void:
    add_force_for_frame(-applied_forces) # wipe out previous forces

    # arrows keys apply force to move it
    # could equally have a different body which pushes it
    if Input.is_action_pressed("ui_right"):
        self.add_force_for_frame(move_strength * Vector2(1, 0))
    if Input.is_action_pressed("ui_left"):
        self.add_force_for_frame(move_strength * Vector2(-1, 0))
    if Input.is_action_pressed("ui_up"):
        self.add_force_for_frame(move_strength * Vector2(0, -1))
    if Input.is_action_pressed("ui_down"):
        self.add_force_for_frame(move_strength * Vector2(0, 1))

    # this bit applies the damping force
    # minus is there because friction resists the direction of motion
    # friction depends on the m * g of the object (in this case the weight)
    if self.linear_velocity.length() == 0:
        self.add_force_for_frame(- self.weight * mu_static * self.linear_velocity.normalized())
    else:
        self.add_force_for_frame(- self.weight * mu_moving * self.linear_velocity.normalized())
    # no worries about collisions as they add their own forces in opposition to these ones

Thank you! It works perfectly !

Hello! I need your help. The script works well and everything, but I have a problem. I want to simulate a tank ~45T. and I want it to stop fast when I release the button. But I can only achieve that with friction coefficient around 20, but that's not really correct cause it can't be greater that 1. Could you advice something?

0 votes

I solved this problem by switching RigidBody2D's mode to Character and then changing angular damp and linear damp parameters to 100

by (38 points)
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.