Godot 4.1 - Have player push a block

Hi there,

I have recently completed the 2d Godot course and wanted to get started creating a new game. The concept is a simple puzzle game in which you need to push blocks onto switches to complete the current scene (ala Brain-Sport on the old Sinclar Spectrum system).

I have a test scene setup and have managed to get the player to move around the tilemap in a grid fashion. Using a RayCast2D, the player can detect an item in front of it, but I am struggling to find a way to have the system to push the object the player is walking into.

Below is the code I have in my player script:

extends Sprite2D

@onready var tile_map = $"../TileMap"
@onready var sprite_2d = $Sprite2D
@onready var ray_cast_2d = $RayCast2D

var is_moving = false

func _physics_process(delta):
	if is_moving == false:
		return
	
	if global_position == sprite_2d.global_position:
		is_moving = false
		return
	
	sprite_2d.global_position = sprite_2d.global_position.move_toward(global_position, 1)

func _process(delta):
	if is_moving:
		return
	if Input.is_action_pressed("up"):
		move(Vector2.UP)
	elif Input.is_action_pressed("down"):
		move(Vector2.DOWN)
	elif Input.is_action_pressed("left"):
		move(Vector2.LEFT)
	elif Input.is_action_pressed("right"):
		move(Vector2.RIGHT)

func move(direction: Vector2):
	# Get current tile Vector2i
	var current_tile: Vector2i = tile_map.local_to_map(global_position)
	# Get target tile Vector2i
	var target_tile: Vector2i = Vector2i(
		current_tile.x + direction.x,
		current_tile.y + direction.y
	)
	
	# Get custom data layer from the target tile
	var tile_data: TileData = tile_map.get_cell_tile_data(0, target_tile)
	
	if tile_data.get_custom_data("walkable") == false:
		return
	
	ray_cast_2d.target_position = direction * 16
	ray_cast_2d.force_raycast_update()
	
	if ray_cast_2d.is_colliding():
		return
	
	# Move player
	is_moving = true
	global_position = tile_map.map_to_local(target_tile)
	sprite_2d.global_position = tile_map.map_to_local(current_tile)

I have an object that is a Area2D with CollisionShape2D and an object that is a RigidBody2D with CollisionShape2D. I have seen the RayCast will return the object that it is colliding with with get_collider but I am struggling to figure out how to get the players direction, check if the path is clear and to then move the object and player in the correct direction. Any tips or advise would be grateful.

Thanks.

been thinking about this, not something ive done. sort of like a sokoban mechanic.
looking around, GDQuest done a similar one here, bit of an older version, but you might get some snippings to help you along there
(3) Code a Simple Puzzle Game in Godot: Box and Switch tutorial - YouTube

Thanks for the feedback. I have managed to do this by having the players RayCast call a move function in the instance of the box and passing the players direction through to it. Took me a few attempts to get working correctly but I got there in the end.

1 Like

nice one, glad you found a workaround

This topic was automatically closed 20 days after the last reply. New replies are no longer allowed.

Privacy & Terms