init
This commit is contained in:
159
Scripts/World.gd
Normal file
159
Scripts/World.gd
Normal file
@@ -0,0 +1,159 @@
|
||||
extends Node2D
|
||||
|
||||
@onready var players_container = $PlayersContainer
|
||||
@onready var tile_map = $Ground
|
||||
|
||||
var player_nodes := {} # id -> Node
|
||||
|
||||
func _ready():
|
||||
$Ground.scale = Vector2(1, 1)
|
||||
if has_node("Water"):
|
||||
$Water.scale = Vector2(1, 1)
|
||||
|
||||
# Clean setup: trust the scene file
|
||||
var entrance = get_node_or_null("NeighborhoodEntrance")
|
||||
if entrance:
|
||||
entrance.monitorable = true
|
||||
entrance.monitoring = true
|
||||
# Ensure it detects Player (Layer 2) OR Layer 1 just in case
|
||||
entrance.collision_mask = 3 # Layers 1 and 2
|
||||
|
||||
if not entrance.body_entered.is_connected(_on_neighborhood_entrance_body_entered):
|
||||
entrance.body_entered.connect(_on_neighborhood_entrance_body_entered)
|
||||
if not entrance.body_exited.is_connected(_on_neighborhood_entrance_body_exited):
|
||||
entrance.body_exited.connect(_on_neighborhood_entrance_body_exited)
|
||||
|
||||
NetworkManager.login_ok.connect(_on_login_ok)
|
||||
NetworkManager.player_joined.connect(_on_player_joined)
|
||||
NetworkManager.player_left.connect(_on_player_left)
|
||||
NetworkManager.player_moved.connect(_on_player_moved)
|
||||
NetworkManager.disconnected.connect(_on_disconnected)
|
||||
|
||||
# Explicitly spawn local player if logged in
|
||||
if NetworkManager.my_id != -1:
|
||||
_spawn_player(NetworkManager.my_id, NetworkManager.player_info["name"], 0, 0, NetworkManager.player_info["skin_id"])
|
||||
|
||||
for id in NetworkManager.players:
|
||||
var p = NetworkManager.players[id]
|
||||
_spawn_player(id, p["name"], p["x"], p["y"], p.get("skin_id", 0))
|
||||
|
||||
var chat = preload("res://Scenes/UI/ChatHUD.tscn").instantiate()
|
||||
add_child(chat)
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
var player_in_entrance := false
|
||||
|
||||
func _on_neighborhood_entrance_body_entered(body):
|
||||
print("Body ENTERED Trigger: ", body.name, " (My ID: ", NetworkManager.my_id, ")")
|
||||
# Check if it's the local player
|
||||
if body.name == str(NetworkManager.my_id):
|
||||
player_in_entrance = true
|
||||
print("Player ENTERED entrance area")
|
||||
|
||||
func _on_neighborhood_entrance_body_exited(body):
|
||||
if body.name == str(NetworkManager.my_id):
|
||||
player_in_entrance = false
|
||||
print("Player EXITED entrance area")
|
||||
|
||||
func _physics_process(_delta):
|
||||
if player_in_entrance:
|
||||
# Check for Up input while inside the entrance
|
||||
if Input.is_action_pressed("ui_up") or Input.is_key_pressed(KEY_W):
|
||||
_do_room_transition()
|
||||
|
||||
func _do_room_transition():
|
||||
var entrance = get_node_or_null("NeighborhoodEntrance")
|
||||
if not entrance:
|
||||
return
|
||||
|
||||
var local_player = player_nodes.get(NetworkManager.my_id)
|
||||
if not local_player:
|
||||
return
|
||||
|
||||
player_in_entrance = false # Prevent re-trigger
|
||||
NetworkManager.next_spawn_position = local_player.position + Vector2(0, 32)
|
||||
NetworkManager.send_change_scene("room_" + str(NetworkManager.my_id), Vector2(0, 0))
|
||||
get_tree().change_scene_to_file("res://Scenes/Room.tscn")
|
||||
|
||||
|
||||
func _fill_background():
|
||||
# Fill base stone floor (standard blue brick at 0,0)
|
||||
# Procedural generation for background
|
||||
# Procedural generation for background
|
||||
for x in range(-50, 150):
|
||||
for y in range(-50, 100):
|
||||
var tile_pos = Vector2i(x, y)
|
||||
|
||||
# Plaza in the center (0 to 15)
|
||||
if x >= 0 and x < 15 and y >= 0 and y < 15:
|
||||
# Use light gray stone coordinates confirmed in TownTileset.tres
|
||||
var rand_var = randi() % 3
|
||||
tile_map.set_cell(tile_pos, 5, Vector2i(4 + rand_var, 0)) # (4,0), (5,0), (6,0)
|
||||
else:
|
||||
# Regular floor (blue-ish / darker)
|
||||
if (x + y) % 2 == 0:
|
||||
tile_map.set_cell(tile_pos, 5, Vector2i(1, 0))
|
||||
else:
|
||||
tile_map.set_cell(tile_pos, 5, Vector2i(2, 0))
|
||||
|
||||
func _on_login_ok(_my_id, _players):
|
||||
pass
|
||||
|
||||
func _on_player_joined(id, p_name, x, y, skin_id):
|
||||
_spawn_player(id, p_name, x, y, skin_id)
|
||||
|
||||
func _on_player_left(id):
|
||||
if player_nodes.has(id):
|
||||
player_nodes[id].queue_free()
|
||||
player_nodes.erase(id)
|
||||
|
||||
func _on_player_moved(id, x, y, flip_h, frame):
|
||||
if player_nodes.has(id):
|
||||
player_nodes[id].set_remote_state(Vector2(x, y), flip_h, frame)
|
||||
|
||||
func _on_disconnected():
|
||||
get_tree().change_scene_to_file("res://Scenes/StartMenu.tscn")
|
||||
|
||||
func _spawn_player(id, _p_name, x, y, _skin_id):
|
||||
# Anti-Ghosting: Check if this player already exists in the tree
|
||||
if players_container.has_node(str(id)):
|
||||
var old_node = players_container.get_node(str(id))
|
||||
old_node.name = "Ghost_" + str(id) # Rename to avoid duplicate name error during queue_free
|
||||
old_node.queue_free()
|
||||
|
||||
# Also clean dictionary
|
||||
if player_nodes.has(id):
|
||||
player_nodes.erase(id)
|
||||
|
||||
var p = preload("res://Scenes/Player.tscn").instantiate()
|
||||
p.name = str(id)
|
||||
|
||||
# Override position if returning from another scene
|
||||
var spawn_pos = Vector2(x, y)
|
||||
if id == NetworkManager.my_id and NetworkManager.next_spawn_position != Vector2.ZERO:
|
||||
spawn_pos = NetworkManager.next_spawn_position
|
||||
# Reset after use
|
||||
NetworkManager.next_spawn_position = Vector2.ZERO
|
||||
|
||||
p.position = spawn_pos
|
||||
p.player_id = id
|
||||
p.is_local = (id == NetworkManager.my_id)
|
||||
print("Spawning Player ID: ", id, " Name: ", _p_name, " Is Local: ", p.is_local, " (My ID: ", NetworkManager.my_id, ")")
|
||||
|
||||
if p.is_local:
|
||||
p.interaction_request.connect(_on_interaction_request)
|
||||
|
||||
players_container.add_child(p)
|
||||
player_nodes[id] = p
|
||||
|
||||
func _on_interaction_request(target_id, target_name):
|
||||
print("World received interaction request for: ", target_name)
|
||||
var chat = get_node_or_null("ChatHUD")
|
||||
if chat:
|
||||
if chat.has_method("set_private_target"):
|
||||
chat.set_private_target(target_id, target_name)
|
||||
else:
|
||||
print("ChatHUD missing set_private_target method")
|
||||
Reference in New Issue
Block a user