move_and_collide doesn't allow for teleporting

Godot Version

Version 4.7.2

Question

This is my first test game I'm making, and it's just pong. Everything so far has worked smoothly, wall bounces off walls using move_and_collide, and the two "bars" on either side bounce the ball as well. The problem comes in where one player scores and the ball resets to the center.

Usually, for something like this you just set position coordinates. That didn’t work, so I set the global_position coordinates as well. Nothing seems to work. I decided to print out their x values and apparently they’re 576 the whole time? Like move_and_collide doesn’t update any position values. I’m not entirely sure how that works. I mean the local position has to be stored somewhere, right? Otherwise the engine wouldn’t be able to display the object moving.

I guess my point is that I’ve done many searches, many different self-tests and everything I try just doesn’t work simply because I don’t have access to the position variables. Currently, my code looks like this:

extends Node2D
var dir_defined = false;
var can_move = false;
var reset_time = 6000;
var reset_clock = 0;
var dirx = 0;
var diry = 0;
var minspeed = 500;
var maxspeed = 1000;
var speed = minspeed;
var basex;
var basey;
# Called when the node enters the scene tree for the first time.
func _ready() -> void:
	position.x = get_viewport_rect().size.x / 2;
	position.y = get_viewport_rect().size.y / 2;
	basex = position.x;
	basey = position.y;
	dirx = randf_range(-1.0, 1.0);
	diry = randf_range(-1.0, 1.0);
	pass # Replace with function body.
	
func reset() -> void:
	var _returnx = 0;
	var _returny = 0;
	if(position.x > basex):
		_returnx = basex - position.x;
	else:
		_returnx = position.x - basex;
	if(position.y > basey):
		_returny = basey.position.y;
	else:
		_returny = position.y - basey;
	position.x = _returnx;
	position.y = _returny;
    $CharacterBody2D.move_and_collide(position); #This is another attempt that doesn't work, since basex - position is always 0. 
	dirx = randf_range(-1.0, 1.0);
	diry = randf_range(-1.0, 1.0);
	
	speed = minspeed;
	print("Rest complete!");
	pass
# Called every frame. 'delta' is the elapsed time since the previous frame.
func _process(delta: float) -> void:
	var velocity = Vector2.ZERO;
	var myscene = get_parent();
	
	if(!dir_defined):
		dir_defined = true;
		
	velocity.x = dirx;
	velocity.y = diry;
	if(can_move):
		var collision = $CharacterBody2D.move_and_collide(velocity * delta * speed);
		if collision != null:
			var body = collision.get_collider();
			dir_defined = false;
			speed += 10;
			speed = clamp(speed, minspeed, maxspeed);
			print(body.name);
			if(body.name == "LeftbarColl" || body.name == "RightBarColl"):
				dirx = -dirx;
				diry = randf_range(-1.0, 1.0);
			elif(body.name == "WallCeil" || body.name == "WallFloor"):
				diry = -diry;
			elif(body.name == "WallLeft" || body.name == "WallRight"):
				can_move = false;
				reset_clock = reset_time * delta;
				reset();
		
		if(velocity.length() > 0):
			velocity = velocity.normalized();
	else:
		reset_clock -= 1;
		if(reset_clock <= 0):
			can_move = true;
		velocity = Vector2.ZERO;
		
	pass

Most of my attempts either end up with the ball sticking to the wall it scored on or disappearing off screen. I apologize in advance if this is a topic that was made before but google hasn’t been able to surface it for me, and mostly is telling me about things in physics (Which as far as I’m aware isn’t what I want)

Why didn’t it work? What did that code look like?

Why is your script on a Node2D instead of the CharacterBody2D itself?

As far as I’m aware it doesn’t work because those variables aren’t being updated with move_and_collide. The ball code is what you’re looking at. As to why its on a Node2D, I didn’t exactly know that that’s where you’re supposed to put it. I experimented with placing code on children of nodes and it sorta just breaks and will say “this function is not apart of the base”.

I’m fairly new at Godot and the whole family tree node thing isn’t something I’m very good with. I can try to move the code to the CharacterBody2D and see what happens though

I’m marking this as the solution since I rewrote the whole code in the CharacterBody2D and is now working as intended. Thanks for your help!