0 votes

Hi everyone! I'm learning to use Godot with the brand new GDNative (C++17) API and I hit a wall. Been hitting hit for like 4 hours...

I'm following the FPS Tutorial from here but converting GDScript code to C++, which looks mostly the same. But, when I move in any direction, it goes in a weird, unexpected direction. In a hope to know if it's my code or the engine that's bugged, I copied the code from the tutorial and replaced my class with it, and it works as expected... Why? What am I doing wrong?

I uploaded the whole project to my Dropbox, with compiled binaries for Windows 64-bit (~2mb) if it is needed.

C++ functions that process movement :

void Player::process_input()
{
    auto xform = _cam->get_global_transform();
    _dir = {};

    auto input_vector = Vector2();

    if (Input::is_action_pressed("move_forward"))
        input_vector.y += 1;
    if (Input::is_action_pressed("move_back"))
        input_vector.y -= 1;
    if (Input::is_action_pressed("move_left"))
        input_vector.x -= 1;
    if (Input::is_action_pressed("move_right"))
        input_vector.x += 1;

    input_vector.normalize();

    _dir += -xform.basis.z.normalized() * input_vector.y;
    _dir += xform.basis.x.normalized() * input_vector.x;

    if (Input::is_action_just_pressed("ui_cancel"))
        Input::set_mouse_mode(Input::get_mouse_mode() == Input::MOUSE_MODE_VISIBLE
            ? Input::MOUSE_MODE_CAPTURED
            : Input::MOUSE_MODE_VISIBLE);
}

void Player::process_movement(double delta)
{
    _dir.y = 0;
    _dir.normalize();

    _vel.y += delta * GRAVITY;

    auto hvel = _vel;
    hvel.y = 0;

    auto target = _dir;
    target *= MAX_SPEED;

    real_t accel = 0;
    if (_dir.dot(hvel) > 0)
        accel = ACCEL;
    else
        accel = DEACCEL;

    hvel = hvel.linear_interpolate(target, accel * (real_t) delta);
    _vel.x = hvel.x;
    _vel.z = hvel.z;
    _vel = owner->move_and_slide(_vel, Vector3(0, 1, 0), 0.05, 4, deg2rad(MAX_SLOPE_ANGLE));
}

The same functions in GDScript :

func process_input(delta):

    # ----------------------------------
    # Walking
    dir = Vector3()
    var cam_xform = camera.get_global_transform()

    var input_movement_vector = Vector2()

    if Input.is_action_pressed("move_forward"):
        input_movement_vector.y += 1
    if Input.is_action_pressed("move_back"):
        input_movement_vector.y -= 1
    if Input.is_action_pressed("move_left"):
        input_movement_vector.x -= 1
    if Input.is_action_pressed("move_right"):
        input_movement_vector.x += 1

    input_movement_vector = input_movement_vector.normalized()

    dir += -cam_xform.basis.z.normalized() * input_movement_vector.y
    dir += cam_xform.basis.x.normalized() * input_movement_vector.x
    # ----------------------------------

    # ----------------------------------
    # Capturing/Freeing the cursor
    if Input.is_action_just_pressed("ui_cancel"):
        if Input.get_mouse_mode() == Input.MOUSE_MODE_VISIBLE:
            Input.set_mouse_mode(Input.MOUSE_MODE_CAPTURED)
        else:
            Input.set_mouse_mode(Input.MOUSE_MODE_VISIBLE)
    # ----------------------------------

func process_movement(delta):
    dir.y = 0
    dir = dir.normalized()

    vel.y += delta * GRAVITY

    var hvel = vel
    hvel.y = 0

    var target = dir
    target *= MAX_SPEED

    var accel
    if dir.dot(hvel) > 0:
        accel = ACCEL
    else:
        accel = DEACCEL

    hvel = hvel.linear_interpolate(target, accel*delta)
    vel.x = hvel.x
    vel.z = hvel.z
    vel = move_and_slide(vel, Vector3(0, 1, 0), 0.05, 4, deg2rad(MAX_SLOPE_ANGLE))
in Engine by (19 points)

1 Answer

0 votes
Best answer

Asked the question on the Discord and found the problem : Basis' axis are transposed in GDNative, I needed to use basis.get_axis(0) instead of basis.x and the same for the other axis. This isn't documented anywhere though...

Thanks to the Discord guys for helping!

by (19 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 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.