0 votes

so i have 2 objects... the first object has basic movement code.. and the second object has "look_at()" code... so everytime i move the first object the second object will always facing the first one.. BUT... i want the second object to move forward forever .. like..its move forward forever to its current angle/ rotation

in Engine by (19 points)
reshown by

1 Answer

0 votes
Best answer

You can do it this way:

func _fixed_process(delta):

    # ...
    # look at
    # ...

    # You need an angle rotated 90 degrees,
    # because look_at considers that an angle of 0 is pointing up, not right.
    # (Adjust it if it's wrong in your case, depends on how your sprite looks)
    var angle = get_rot() - PI/2.0

    # Define some speed
    var speed = 10.0

    # Calculate direction:
    # the Y coordinate must be inverted,
    # because in 2D the Y axis is pointing down
    var dir = Vector2(cos(angle), -sin(angle))

    # Move
    set_pos(get_pos() + dir * (speed * delta))
by (28,882 points)
selected by

no shorter code than that ?

The code look long because I heavily commented it.
You can use move too, but I don't know if it can make the code shorter.
It would be like this:

move(dir * (speed * delta))

In order for your node to move in a given direction (dir), you need that direction. All you have is an angle (one number), so you must convert that angle into a vector (x and y) using simple trigonometry.

You also need to define at which speed you want your object to move. In my code I just defined it on the fly as 10 pixels per second, but you can put it as a member variable of your script, or as a constant if you want.

In Godot, delta is the parameter received by _fixed_process and _process. It contains the amount of time elapsed between two frames.
It needs to be a multiplier of speed because in this way, your game won't slow down if the game lags, and won't be faster if FPS increases, it will stay at the speed you want.

Writing move(vector2(the x and y pos) is possible indeed, that's what I do, because when you multiply dir by a number (speed * delta) you still obtain a vector, representing the "amount of distance in X and Y to move for this frame". That's basic vector math ;)

However, I agree the extra rotations I added are a bit cumbersome, but they are needed due to 2D conventions in Godot, and also because it depends how you drew your sprite. My code assumes the sprite looks at the right in its image file, but if you made it look up, you don't need it. And if it was looking left, you would need the opposite etc.

If you want to get a directional vector and not worry too much about the math, you can use get_transform() (or getglobaltransform if that's what you need). This gives you three elements to work with; origin (basically what you'd get with getpos()), and local vectors for x (facing right) and y (facing down).
If you're using look
at(), it's going to be pointing that y vector in the direction you want it to look, so if you want it to move in that direction:

var dir = get_transform().y
move(dir*speed*delta)

Ah yeah, almost forgot this. It looks cleaner indeed, but you might prefer getting the x vector in case the sprite is right-oriented.

understand all already.. thx.. but what about the "angle" variable code ? why do i need to substract it with PI ? and divide it by 2 ???

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.