* Added console
* Set the game to automatically start a server and client. * Made it so second player can pick up pot correctly and move it around. * Still buggy when putting it down. * Disabled "Countdown" as it became annoying when testing.
This commit is contained in:
@@ -8,8 +8,14 @@ var entity_id = ""
|
||||
var object_name = "bomb"
|
||||
|
||||
@export var is_being_thrown = false
|
||||
@export var is_being_lifted = false
|
||||
@export var is_being_put_down = false
|
||||
@export var is_being_lifted = false:
|
||||
set(value):
|
||||
is_being_lifted = value
|
||||
Console.print("Pot is_being_lifted changed to: ", value, " on peer: ", multiplayer.get_unique_id())
|
||||
@export var is_being_put_down = false:
|
||||
set(value):
|
||||
is_being_put_down = value
|
||||
Console.print("Pot is_being_put_down changed to: ", value, " on peer: ", multiplayer.get_unique_id())
|
||||
@export var is_being_grabbed = false
|
||||
@export var is_moving = false
|
||||
@export var is_spawning = false
|
||||
@@ -44,6 +50,24 @@ var re_enable_time = 0.17
|
||||
var previousFrameVel = Vector2.ZERO
|
||||
var hasShownSmokePuffs = false
|
||||
|
||||
@export var holder_peer_id: int = 0:
|
||||
set(value):
|
||||
holder_peer_id = value
|
||||
Console.print("Pot holder_peer_id changed to: ", value, " on peer: ", multiplayer.get_unique_id())
|
||||
# Clear lifting state when holder is cleared, but only if we're not in the middle of lifting
|
||||
if value == 0 and !is_being_lifted:
|
||||
is_being_lifted = false
|
||||
holder = null
|
||||
elif value != 0:
|
||||
# Find the holder by peer ID
|
||||
var spawn_root = get_tree().get_current_scene().get_node("SpawnRoot")
|
||||
if spawn_root:
|
||||
holder = spawn_root.get_node_or_null(str(value))
|
||||
if holder:
|
||||
Console.print("Pot found holder: ", holder.name, " for peer ID: ", value)
|
||||
else:
|
||||
Console.print("Pot failed to find holder for peer ID: ", value)
|
||||
|
||||
func _ready() -> void:
|
||||
if is_spawning:
|
||||
liftable = false
|
||||
@@ -58,6 +82,51 @@ func _ready() -> void:
|
||||
pass
|
||||
|
||||
func _physics_process(delta: float) -> void:
|
||||
# Update holder based on holder_peer_id for network sync
|
||||
if holder_peer_id != 0:
|
||||
var player = get_tree().get_current_scene().get_node("SpawnRoot").get_node_or_null(str(holder_peer_id))
|
||||
if player and holder != player:
|
||||
Console.print("Pot updating holder from ", holder, " to ", player.name)
|
||||
holder = player
|
||||
# Ensure lifting state is synced when holder changes
|
||||
if !is_being_lifted and !is_being_grabbed:
|
||||
is_being_lifted = true
|
||||
lift_progress = 0.0
|
||||
elif !player:
|
||||
Console.print("Pot could not find player with peer_id: ", holder_peer_id)
|
||||
elif holder_peer_id == 0 and holder != null:
|
||||
Console.print("Pot clearing holder (holder_peer_id is 0)")
|
||||
holder = null
|
||||
is_being_lifted = false
|
||||
|
||||
# Handle lifted pot position on ALL clients for smooth following
|
||||
if is_being_lifted and holder:
|
||||
$GPUParticles2D.emitting = false
|
||||
if lift_progress < 1.0:
|
||||
lift_progress += delta * lift_speed
|
||||
lift_progress = min(lift_progress, 1.0)
|
||||
|
||||
# Smoothly interpolate from current position to above holder during lifting
|
||||
var target_pos = holder.global_position + Vector2(0, -8)
|
||||
if lift_progress < 1.0:
|
||||
global_position = global_position.lerp(target_pos, lift_progress)
|
||||
positionZ = lift_height * lift_progress
|
||||
else:
|
||||
# When fully lifted, maintain exact position above holder
|
||||
global_position = target_pos
|
||||
positionZ = lift_height
|
||||
else:
|
||||
# Debug: Check why pot is not following
|
||||
if is_being_lifted and !holder:
|
||||
Console.print("Pot is_being_lifted but holder is null! holder_peer_id: ", holder_peer_id)
|
||||
# Fix inconsistent state
|
||||
if holder_peer_id == 0:
|
||||
is_being_lifted = false
|
||||
elif !is_being_lifted and holder:
|
||||
# Pot has holder but is_being_lifted is false - this is normal during transitions
|
||||
pass
|
||||
update_sprite_scale()
|
||||
|
||||
if multiplayer.is_server():
|
||||
if is_being_thrown:
|
||||
re_enable_collision_after_time -= delta
|
||||
@@ -81,7 +150,7 @@ func _physics_process(delta: float) -> void:
|
||||
$GPUParticles2D.emitting = true
|
||||
$GPUParticles2D/TimerSmokeParticles.start()
|
||||
if abs(velocityZ) > minBounceVelocity:
|
||||
velocityZ = -velocityZ * bounceRestitution
|
||||
velocityZ = - velocityZ * bounceRestitution
|
||||
else:
|
||||
velocityZ = 0
|
||||
is_being_thrown = false
|
||||
@@ -117,23 +186,7 @@ func _physics_process(delta: float) -> void:
|
||||
global_position = put_down_start_pos.lerp(put_down_target_pos, 1.0 - lift_progress)
|
||||
positionZ = lift_height * lift_progress
|
||||
update_sprite_scale()
|
||||
elif is_being_lifted:
|
||||
# Smooth lifting animation
|
||||
if holder:
|
||||
$GPUParticles2D.emitting = false
|
||||
target_position = holder.global_position
|
||||
#target_position.y -= 2
|
||||
if lift_progress < 1.0:
|
||||
lift_progress += delta * lift_speed
|
||||
lift_progress = min(lift_progress, 1.0)
|
||||
global_position = global_position.lerp(target_position, lift_progress)
|
||||
positionZ = lift_height * lift_progress
|
||||
else:
|
||||
lift_progress = 1.0
|
||||
global_position = target_position
|
||||
positionZ = lift_height
|
||||
update_sprite_scale()
|
||||
pass
|
||||
|
||||
elif is_being_grabbed:
|
||||
#if velocity != Vector2.ZERO and velocity != previousFrameVel and hasShownSmokePuffs == false:
|
||||
if velocity != Vector2.ZERO:
|
||||
@@ -150,7 +203,7 @@ func _physics_process(delta: float) -> void:
|
||||
move_and_collide(velocity * delta)
|
||||
previousFrameVel = velocity
|
||||
pass
|
||||
else: # it just spawned:
|
||||
elif !is_being_lifted: # it just spawned or is free-falling:
|
||||
# Apply gravity to vertical movement
|
||||
velocityZ += accelerationZ * delta
|
||||
positionZ += velocityZ * delta
|
||||
@@ -171,7 +224,7 @@ func _physics_process(delta: float) -> void:
|
||||
$GPUParticles2D.emitting = true
|
||||
$GPUParticles2D/TimerSmokeParticles.start()
|
||||
if abs(velocityZ) > minBounceVelocity:
|
||||
velocityZ = -velocityZ * bounceRestitution
|
||||
velocityZ = - velocityZ * bounceRestitution
|
||||
else:
|
||||
velocityZ = 0
|
||||
velocity = velocity.lerp(Vector2.ZERO, 0.5)
|
||||
@@ -203,6 +256,19 @@ func _physics_process(delta: float) -> void:
|
||||
if $SfxDrag2.playing:
|
||||
$SfxDrag2.stop()
|
||||
$GPUParticles2D.emitting = false
|
||||
# Update position on client to follow holder
|
||||
if holder:
|
||||
target_position = holder.global_position + Vector2(0, -8)
|
||||
if lift_progress < 1.0:
|
||||
lift_progress += delta * lift_speed
|
||||
lift_progress = min(lift_progress, 1.0)
|
||||
global_position = global_position.lerp(target_position, lift_progress)
|
||||
positionZ = lift_height * lift_progress
|
||||
else:
|
||||
# When fully lifted, maintain exact position above holder
|
||||
global_position = target_position
|
||||
positionZ = lift_height
|
||||
update_sprite_scale()
|
||||
elif is_being_grabbed:
|
||||
if is_moving:
|
||||
$GPUParticles2D.emitting = true
|
||||
@@ -224,6 +290,10 @@ func _physics_process(delta: float) -> void:
|
||||
if $SfxDrag2.playing:
|
||||
$SfxDrag2.stop()
|
||||
pass
|
||||
# Fix stuck put_down state
|
||||
if is_being_put_down and lift_progress <= 0:
|
||||
Console.print("Pot is_being_put_down but lift_progress is 0, clearing state")
|
||||
is_being_put_down = false
|
||||
update_sprite_scale()
|
||||
if is_destroyed and !destroy_initiated:
|
||||
destroy_initiated = true
|
||||
@@ -238,7 +308,7 @@ func update_sprite_scale() -> void:
|
||||
var posY = positionZ # Direct mapping of Z to Y offset
|
||||
var sc = 1.0 + (0.1 * height_factor) # Slightly less scale change than loot (0.3 instead of 0.8)
|
||||
$Sprite2D.scale = Vector2(sc, sc)
|
||||
$Sprite2D.offset.y = -posY
|
||||
$Sprite2D.offset.y = - posY
|
||||
# Also update shadow position and scale
|
||||
if is_being_lifted:
|
||||
$Sprite2D.z_as_relative = false
|
||||
@@ -249,7 +319,7 @@ func update_sprite_scale() -> void:
|
||||
$Sprite2D.z_index = 0
|
||||
$Sprite2DShadow.offset.y = 0
|
||||
#$Sprite2DShadow.scale = Vector2(1.125 * sc, 0.5 * sc) # Scale shadow with height
|
||||
$Sprite2DShadow.scale = Vector2(1,1)
|
||||
$Sprite2DShadow.scale = Vector2(1, 1)
|
||||
#$Sprite2DShadow.modulate.
|
||||
|
||||
func throw(direction: Vector2, initial_velocity: float = 200):
|
||||
@@ -262,23 +332,34 @@ func throw(direction: Vector2, initial_velocity: float = 200):
|
||||
is_being_put_down = false
|
||||
thrown_by = holder
|
||||
holder = null
|
||||
holder_peer_id = 0 # Clear the network holder reference
|
||||
velocity = direction * initial_velocity
|
||||
velocityZ = throw_height
|
||||
positionZ = lift_height
|
||||
current_height = 0
|
||||
re_enable_collision_after_time = re_enable_time
|
||||
|
||||
@rpc("any_peer", "reliable")
|
||||
func throw_rpc(direction: Vector2, initial_velocity: float = 200):
|
||||
Console.print("Pot throw_rpc called on peer: ", multiplayer.get_unique_id())
|
||||
# Only execute on server to avoid conflicts
|
||||
if multiplayer.is_server():
|
||||
throw(direction, initial_velocity)
|
||||
|
||||
func grab(new_holder: CharacterBody2D) -> bool:
|
||||
if positionZ <= 0 and holder == null: # only allow grab if no previous owner and position is 0
|
||||
$GPUParticles2D/TimerSmokeParticles.stop() #reset...
|
||||
$GPUParticles2D/TimerSmokeParticles.stop() # reset...
|
||||
holder = new_holder
|
||||
holder_peer_id = new_holder.get_multiplayer_authority()
|
||||
is_being_grabbed = true
|
||||
indicate(false)
|
||||
return true
|
||||
return false
|
||||
|
||||
func release():
|
||||
Console.print("Pot release() called on peer: ", multiplayer.get_unique_id())
|
||||
holder = null
|
||||
holder_peer_id = 0
|
||||
is_being_grabbed = false
|
||||
hasShownSmokePuffs = false
|
||||
indicate(true)
|
||||
@@ -287,6 +368,8 @@ func release():
|
||||
pass
|
||||
|
||||
func lift(new_holder: CharacterBody2D):
|
||||
Console.print("Pot lift() called with holder: ", new_holder.name if new_holder else "null")
|
||||
Console.print("Pot current authority: ", get_multiplayer_authority())
|
||||
if (new_holder != holder and holder != null) and "lose_held_entity" in holder:
|
||||
# steal from holder
|
||||
holder.lose_held_entity(self)
|
||||
@@ -294,6 +377,7 @@ func lift(new_holder: CharacterBody2D):
|
||||
$Area2DCollision.set_deferred("monitoring", false)
|
||||
thrown_by = null
|
||||
holder = new_holder
|
||||
holder_peer_id = new_holder.get_multiplayer_authority()
|
||||
# disable collisions
|
||||
self.set_collision_layer_value(8, false)
|
||||
self.set_collision_mask_value(7, false)
|
||||
@@ -306,7 +390,23 @@ func lift(new_holder: CharacterBody2D):
|
||||
is_being_put_down = false
|
||||
lift_progress = 0.0
|
||||
velocityZ = 0
|
||||
# Store initial position for smooth lifting - don't change current position yet
|
||||
# The pot will smoothly glide from its current position to above the holder
|
||||
$SfxLand.play()
|
||||
Console.print("Pot lift() completed, is_being_lifted: ", is_being_lifted)
|
||||
|
||||
@rpc("any_peer", "reliable")
|
||||
func lift_rpc(holder_path: NodePath):
|
||||
Console.print("Pot lift_rpc called with holder_path: ", holder_path, " on peer: ", multiplayer.get_unique_id())
|
||||
# Only execute on server to avoid conflicts
|
||||
if multiplayer.is_server():
|
||||
# Find the holder by path
|
||||
var holder_node = get_node_or_null(holder_path)
|
||||
if holder_node and holder_node is CharacterBody2D:
|
||||
Console.print("Pot found holder, calling lift()")
|
||||
lift(holder_node)
|
||||
else:
|
||||
Console.print("Pot failed to find holder at path: ", holder_path)
|
||||
|
||||
func put_down() -> bool:
|
||||
if not is_being_lifted or is_being_put_down:
|
||||
@@ -365,13 +465,13 @@ func put_down() -> bool:
|
||||
put_down_start_pos = global_position
|
||||
thrown_by = null
|
||||
holder = null
|
||||
holder_peer_id = 0
|
||||
|
||||
indicate(true)
|
||||
|
||||
return true
|
||||
|
||||
func remove():
|
||||
|
||||
var fade_tween = create_tween()
|
||||
fade_tween.set_trans(Tween.TRANS_CUBIC)
|
||||
fade_tween.set_ease(Tween.EASE_OUT)
|
||||
@@ -442,7 +542,6 @@ func _on_area_2d_collision_body_entered(body: Node2D) -> void:
|
||||
if is_being_thrown == false or body == self or body == thrown_by:
|
||||
return
|
||||
if multiplayer.is_server():
|
||||
|
||||
var collision_shape = $Area2DCollision.get_overlapping_bodies()
|
||||
|
||||
if collision_shape.size() > 0:
|
||||
@@ -477,6 +576,55 @@ func show_destroy_effect():
|
||||
self.call_deferred("remove")
|
||||
pass
|
||||
|
||||
@rpc("any_peer", "reliable")
|
||||
func request_grab_pot(pot_path: NodePath, peer_id: int):
|
||||
if multiplayer.is_server():
|
||||
var pot = get_node_or_null(pot_path)
|
||||
var player = get_tree().get_current_scene().get_node("SpawnRoot").get_node_or_null(str(peer_id))
|
||||
if pot and "grab" in pot and player:
|
||||
if pot.grab(player):
|
||||
player.grabbed_entity = pot
|
||||
player.grabbed_entity_path = str(pot.get_path())
|
||||
player.current_animation = "IDLE_PUSH"
|
||||
# Sync animation and entity to all clients
|
||||
#var all_players = get_tree().get_current_scene().get_node("SpawnRoot").get_children()
|
||||
#for p in all_players:
|
||||
#if p.has_method("sync_animation"):
|
||||
#p.sync_animation.rpc("IDLE_PUSH")
|
||||
#p.sync_grabbed_entity.rpc(str(pot.get_path()))
|
||||
|
||||
@rpc("any_peer", "reliable")
|
||||
func request_lift_pot(pot_path: NodePath, peer_id: int):
|
||||
# This function is now handled by MultiplayerManager
|
||||
# Keeping it for backward compatibility but it should not be called
|
||||
print("Pot received request_lift_pot RPC - this should be handled by MultiplayerManager")
|
||||
pass
|
||||
|
||||
@rpc("any_peer", "reliable")
|
||||
func request_throw_pot(pot_path: NodePath, peer_id: int, direction: Vector2):
|
||||
if multiplayer.is_server():
|
||||
var pot = get_node_or_null(pot_path)
|
||||
var player = get_tree().get_current_scene().get_node("SpawnRoot").get_node_or_null(str(peer_id))
|
||||
print("Throw request: pot=", pot, " player=", player, " pot.holder_peer_id=", pot.holder_peer_id if pot else "null", " peer_id=", peer_id)
|
||||
if pot and player:
|
||||
# Check if the pot is being held by this player (either by holder_peer_id or by checking the holder directly)
|
||||
if pot.holder_peer_id == peer_id or (pot.holder != null and pot.holder.get_multiplayer_authority() == peer_id):
|
||||
print("Throw authorized for peer ", peer_id)
|
||||
pot.throw(direction)
|
||||
player.held_entity = null
|
||||
player.held_entity_path = ""
|
||||
player.current_animation = "THROW"
|
||||
# Sync pot state to all clients first
|
||||
pot.sync_pot_state.rpc(false, 0) # Not lifted, no holder
|
||||
# Sync animation and clear held entity to all clients
|
||||
var all_players = get_tree().get_current_scene().get_node("SpawnRoot").get_children()
|
||||
for p in all_players:
|
||||
if p.has_method("sync_animation"):
|
||||
p.sync_animation.rpc("THROW")
|
||||
p.sync_held_entity.rpc("") # Clear held entity
|
||||
else:
|
||||
print("Throw denied: holder_peer_id mismatch or holder not found")
|
||||
|
||||
@rpc("call_local")
|
||||
func take_damage(_iBody: Node2D, _iByWhoOrWhat: Node2D) -> void:
|
||||
is_destroyed = true # will trigger show_destroy_effect for clients...
|
||||
@@ -490,6 +638,21 @@ func take_damage(_iBody: Node2D, _iByWhoOrWhat: Node2D) -> void:
|
||||
self.set_collision_mask_value(10, false)
|
||||
pass
|
||||
|
||||
@rpc("call_local", "reliable")
|
||||
func sync_pot_state(lifted: bool, holder_id: int):
|
||||
is_being_lifted = lifted
|
||||
holder_peer_id = holder_id
|
||||
if holder_peer_id != 0:
|
||||
var player = get_tree().get_current_scene().get_node("SpawnRoot").get_node_or_null(str(holder_peer_id))
|
||||
if player:
|
||||
holder = player
|
||||
else:
|
||||
holder = null
|
||||
else:
|
||||
holder = null
|
||||
print("Pot state synced: lifted=", lifted, " holder_id=", holder_id)
|
||||
pass
|
||||
|
||||
func _on_area_2d_collision_body_exited(_body: Node2D) -> void:
|
||||
pass # Replace with function body.
|
||||
|
||||
|
||||
Reference in New Issue
Block a user