feat: Add core map generation and management system
- Introduced MapData, MapGenerator, and MapPainter classes for procedural map generation. - Implemented LevelManager to handle level initialization and navigation. - Created TurnManager for managing turn order in a turn-based system. - Added Player and Enemy character classes with movement and turn-taking capabilities. - Established pathfinding using AStar2D in PathfindingHandler. - Integrated new scenes for player and enemy characters, along with world setup. - Included a new tileset for futuristic Zelda-themed assets.
This commit is contained in:
@@ -0,0 +1,26 @@
|
||||
## Character.gd
|
||||
# Base class for all turn-based characters (player, enemies, etc.)
|
||||
# Handles registration with TurnManager and provides a turn interface.
|
||||
class_name Character
|
||||
extends CharacterBody2D
|
||||
|
||||
# Signal emitted when this character's turn is finished.
|
||||
signal turn_finished
|
||||
|
||||
# Called by TurnManager to let this character take its turn.
|
||||
# Subclasses should override this to implement their own turn logic.
|
||||
func take_turn() -> void:
|
||||
# Virtual method to be overridden by subclasses
|
||||
pass
|
||||
|
||||
# Called when the node enters the scene tree.
|
||||
# Registers this character with the TurnManager for turn order.
|
||||
func _ready() -> void:
|
||||
if Engine.is_editor_hint():
|
||||
return
|
||||
TurnManager.register_entity(self)
|
||||
|
||||
# Call this to remove the character from the turn system and free it from the scene.
|
||||
func die() -> void:
|
||||
TurnManager.unregister_entity(self)
|
||||
queue_free()
|
||||
@@ -0,0 +1,41 @@
|
||||
## player.gd
|
||||
# Player character script. Handles input, pathfinding, and movement.
|
||||
class_name Player
|
||||
extends Character
|
||||
|
||||
# Movement speed in pixels per second.
|
||||
const SPEED: float = 250.0
|
||||
# Distance threshold for snapping to a tile (prevents jitter).
|
||||
const ARRIVAL_THRESHOLD: float = 4.0
|
||||
|
||||
|
||||
# The current path (as a list of tile coordinates) the player is following.
|
||||
var _path: Array[Vector2i] = []
|
||||
|
||||
|
||||
# Handles mouse input for movement. Calculates a path to the clicked tile.
|
||||
func _unhandled_input(event: InputEvent) -> void:
|
||||
if event is InputEventMouseButton and event.button_index == MOUSE_BUTTON_LEFT and event.pressed:
|
||||
var clicked_tile: Vector2i = LevelManager.world_to_tile(get_global_mouse_position())
|
||||
var current_tile: Vector2i = LevelManager.world_to_tile(position)
|
||||
_path = LevelManager.find_path(current_tile, clicked_tile)
|
||||
# Drop the first entry — it's the tile the player is already on.
|
||||
if not _path.is_empty():
|
||||
_path.remove_at(0)
|
||||
|
||||
# Moves the player along the path, one tile at a time, using velocity.
|
||||
func _physics_process(_delta: float) -> void:
|
||||
if _path.is_empty():
|
||||
velocity = Vector2.ZERO
|
||||
move_and_slide()
|
||||
return
|
||||
|
||||
var target_world: Vector2 = LevelManager.tile_to_world(_path[0])
|
||||
var to_target: Vector2 = target_world - position
|
||||
|
||||
if to_target.length() < ARRIVAL_THRESHOLD:
|
||||
position = target_world
|
||||
_path.remove_at(0)
|
||||
else:
|
||||
velocity = to_target.normalized() * SPEED
|
||||
move_and_slide()
|
||||
@@ -0,0 +1,30 @@
|
||||
## world.gd
|
||||
# Main world node script. Sets up the map, player, and level on scene ready.
|
||||
extends Node
|
||||
|
||||
# Reference to the TileMapLayer node for rendering the map.
|
||||
|
||||
# Reference to the TileMapLayer node for rendering the map.
|
||||
var map_layer: TileMapLayer
|
||||
# Path to the Player scene to instance.
|
||||
const PLAYER_SCENE_PATH: String = "res://scenes/actors/player.tscn"
|
||||
# Reference to the Player node.
|
||||
var player: Player
|
||||
# Map generation settings (size, room count, etc.).
|
||||
var settings: MapSettings = MapSettings.new()
|
||||
|
||||
# Called when the node is added to the scene tree.
|
||||
# Initializes references and triggers map setup.
|
||||
func _ready() -> void:
|
||||
map_layer = $MapLayer
|
||||
# Do not assume Player is already in the scene tree; instance it after map generation.
|
||||
call_deferred("_initialize_map")
|
||||
|
||||
# Initializes the map and level using LevelManager.
|
||||
# Ensures the map is generated and the player is placed.
|
||||
func _initialize_map() -> void:
|
||||
# Instance the Player after the map is generated and add to the scene tree.
|
||||
var player_scene: PackedScene = load(PLAYER_SCENE_PATH)
|
||||
player = player_scene.instantiate() as Player
|
||||
add_child(player)
|
||||
LevelManager.initialize(settings, map_layer, player)
|
||||
Reference in New Issue
Block a user