Compare commits

..

5 Commits

Author SHA1 Message Date
f0a60217bc Starting State Aware Sound Effects 2025-03-30 19:24:19 -07:00
85653ba634 Ladder climbing 2025-03-30 18:26:20 -07:00
a230a976aa Level Transition enhance 2025-03-30 12:01:46 -07:00
adebb005ab Climb edge now directional 2025-03-30 11:40:59 -07:00
7e9227064b Level transition improvments. 2025-03-30 11:15:07 -07:00
23 changed files with 263 additions and 227 deletions

Binary file not shown.

Before

Width:  |  Height:  |  Size: 2.6 KiB

After

Width:  |  Height:  |  Size: 2.8 KiB

View File

@ -1,133 +0,0 @@
class_name DumbOldStateModifier
extends Reference
## State modification
##
## A state modifier doesn't have any direct control of a game object.
## They are transfered from the enter and exit of other states and
## influence the movement or animation of their parent states.
## Rather than going full into paralell state machines I hope that this
## modifier will be suitable for a basic state machine.
##
## @WIP
enum TYPE {NONE,EXIT_ANIMATION, ANIMATION_SUFFIX, REPLACE_ANIMATION}
var debug_state: bool = false
## These should be the original properties set when the modifier is created.
# property changes can be applied over time but these are the instantiated values.
var modifier_properties: ModifierProperties
## Animation modifier variables
## The name of the animation that could be applied and starting frame
var animation_name: String
var starting_frame: int = 0
##TODO: Animation speed
## Modification Type
## if an animation is specified, the default behavior will be just to override
## the state animation. Or perform a 'Replace Animation'
var modifier_type = TYPE.NONE
var name :String = ''
# Move Speed in Pixels Per Second
# These should only apply if Modification Type Set to None.
# (But I'm not sure if I like that model.)
#var move_speed: float
#var move_speed_modifier: float = 0
#var move_speed_modifier_decay: float = 0
var gravity: int = ProjectSettings.get_setting("physics/2d/default_gravity")
# Attempting to use this as an animation suffix that can linger after
# state transition like 'run-fire' to 'idle-fire' 'jump-fire' etc.
#var animation_suffix: bool = false
#var pre_append_animation: bool = false
# not sure if I can do the array thing from state change. Maybe?
# disabling this sequencing for now.
# export(Array, String) var animation_sequence
# var animation_index: int = 0
# var current_animation_sequence: int = 0
#var animation_sequence_timer: Timer
var state_timeout: Timer
var timeout_seconds: float = 0.0
# Meant to be called on timeout or other counters this modifier may have.
# Should be updated whenever modifier owner transfers
var state_call_function: FuncRef
## Can't do it this way.
#func copy_modifier() -> StateModifier:
# var new_modifier = StateModifier.new()
# new_modifier.ready(animation_name, modifier_type, timeout_seconds)
#
# return StateModifier.new()
#
func merge_modifier(merging_mod: ModifierProperties):
if merging_mod.modifier_type != TYPE.NONE:
print("Warning Merging modifier types that aren't set to 'none' is not supported!")
return
# Can't support timeouts or animation stuff right now.
#timeout_seconds = merging_mod.timeout_seconds
# move_speed = merging_mod.move_speed
# gravity = merging_mod.gravity
# move_speed_modifier = merging_mod.move_speed_modifier
# move_speed_modifier_decay = merging_mod.move_speed_modifier_decay
func get_modifier_properties() -> ModifierProperties:
#( p_move_speed:float, p_gravity:int , p_move_acceleration , p_move_speed_modifier:float,
# p_move_modifier_move_acceleration:float, p_jerk_factor: float):
var mp = ModifierProperties.new( modifier_properties.move_speed,
modifier_properties.gravity,
modifier_properties.move_acceleration,
modifier_properties.move_speed_modifier,
modifier_properties.move_modifier_move_acceleration,
modifier_properties.jerk_factor)
mp.directional_modifier = modifier_properties.directional_modifier
return mp
func ready(modifier_name:String, anim_name:String = '', type = TYPE.NONE, timeout : float = 0, parent:Node = null, function_name : String = "") -> Timer:
name = modifier_name
# If somebody forgot to specify the type
if anim_name != '' and type == TYPE.NONE:
modifier_type = TYPE.REPLACE_ANIMATION
animation_name = anim_name
modifier_type = type
# if parent != null and function_name != "":
# state_call_function = funcref(parent, function_name)
modifier_properties = ModifierProperties.new(0,0,0,0,0,0)
if timeout > 0:
state_timeout = Timer.new()
state_timeout.wait_time = timeout
state_timeout.one_shot = true
state_timeout.autostart = false
return state_timeout
#add_child(state_timeout)
#ModifierProperties.new()
return null
## Transfer and callback related methods. These sort of worked but I didn't end up using them
## They're an interesting idea though.
func transfer_owner(parent:Node):
print("Modifier owner will now be: ", parent.name)
state_call_function = funcref(parent, 'update_animation')
func _on_Timer_timeout():
#print("Oh Crap! I can't beleive it worked")
if state_call_function:
if state_call_function.is_valid():
state_call_function.call_func()
else:
print("Warning! Modifier timed out with no callback to alert.")
else:
print("Warning! no function applies.")

View File

@ -1,28 +0,0 @@
class_name DEPR_ModifierProperties
extends Reference
var modifier_type: int = 0
#var timeout_seconds: float = 0.0
var move_speed: float = 0.0
var move_acceleration: float = 0.0
var move_speed_modifier: float = 0.0
var move_modifier_move_acceleration: float = 0.0
var jerk_factor: float = 0
var gravity:int = 0
# Bad name. Just means that it is intended to apply in a certain direction
# (Positive or negative) not an offset of the existing values.
var directional_modifier: bool = false
func _init( p_move_speed:float, p_gravity:int , p_move_acceleration , p_move_speed_modifier:float,
p_move_modifier_move_acceleration:float, p_jerk_factor: float):
#timeout_seconds = p_timeout_seconds
move_speed = p_move_speed
move_acceleration = p_move_acceleration
gravity = p_gravity
move_speed_modifier = p_move_speed_modifier
move_modifier_move_acceleration = p_move_modifier_move_acceleration
jerk_factor = p_jerk_factor

View File

@ -6,7 +6,6 @@ extends KinematicBody2D
export(String, "Player", "Enemy", "NPC", "Object") var actor_type export(String, "Player", "Enemy", "NPC", "Object") var actor_type
#export var sprite_facing_right: bool = true #export var sprite_facing_right: bool = true
export(Array, Resource) var SoundEffects
export var debug_actor: bool = false export var debug_actor: bool = false
@ -20,7 +19,6 @@ onready var movement_component: Movement_StateReceiver = $Movement_StateReceiver
#onready var movement_state_machine: StateMachineAnimatedActor = $movement_state_machine #onready var movement_state_machine: StateMachineAnimatedActor = $movement_state_machine
onready var movement_state_machine: StateMachine = $Movement_StateMachine onready var movement_state_machine: StateMachine = $Movement_StateMachine
var sound_effects_dict: Dictionary
##TODO: ##TODO:
# Can't seem to implement the ready and process node functions # Can't seem to implement the ready and process node functions
@ -29,19 +27,11 @@ var sound_effects_dict: Dictionary
# interfaces for the state machines. # interfaces for the state machines.
func _ready() -> void: func _ready() -> void:
pass
#movement_state_machine.init_animated_actor(self) #movement_state_machine.init_animated_actor(self)
#movement_component.attack_function = funcref(self, "attack") #movement_component.attack_function = funcref(self, "attack")
# movement_component.player_number = player_number # movement_component.player_number = player_number
# Experimenting with sound based resources I did this and it worked
#sound_effect_player.stream = sound_effects.sounds["pew"]
#print(sounds.sounds["pew"])
#sound_effects.play()
# Trying something new with a custom resourse.
for i in SoundEffects:
sound_effects_dict[i.animation_name + str(i.frame_number)] = i.sound
print (sound_effects_dict)
func _unhandled_input(event: InputEvent) -> void: func _unhandled_input(event: InputEvent) -> void:
if actor_type == "Player": if actor_type == "Player":
@ -64,20 +54,6 @@ func _physics_process(delta: float) -> void:
# #play_sound_frame(movement_animations.animation , movement_animations.frame) # #play_sound_frame(movement_animations.animation , movement_animations.frame)
var last_sound_frame_animation: String = ''
var last_sound_frame: int = -1
func play_sound_frame(animation: String, frame: int ):
##DEBUG:
#if animation == 'run' and frame == 6:
# print("Do the thign! (", animation + str(frame), ")", " (", last_sound_frame_animation + str(last_sound_frame), ")")
if animation != last_sound_frame_animation or frame != last_sound_frame:
last_sound_frame = frame
last_sound_frame_animation = animation
var sound_index = animation + str(frame)
if sound_effects_dict.has(sound_index):
sound_effect_player.stream = sound_effects_dict[sound_index]
sound_effect_player.play()
print(self.name, " Playing SE: ", sound_index)
func attack(): func attack():
#print(self.name, ": It's not inheritence, it's funcrefs") #print(self.name, ": It's not inheritence, it's funcrefs")

View File

@ -42,6 +42,7 @@ func _ready():
# Sprites should only have a process function # Sprites should only have a process function
# but if I have this will the sprite still animate? # but if I have this will the sprite still animate?
func _process(delta): func _process(delta):
current_state.animation_frame = frame
##TODO: Put in to try to buffer animation switches on frame change ##TODO: Put in to try to buffer animation switches on frame change
if _frame_switch_tracker != -1 and frame == _frame_switch_tracker: if _frame_switch_tracker != -1 and frame == _frame_switch_tracker:
print ("time to switch", _frame_switch_tracker) print ("time to switch", _frame_switch_tracker)

View File

@ -0,0 +1,64 @@
class_name AudioStreamPlayer_StateReceiver
extends AudioStreamPlayer
export var debug_component: bool = false
export var callable_state_machine :NodePath
var request_state_change: FuncRef
export(Array, Resource) var sound_effects
onready var current_state = StateAnimatedActor.new()
# Declare member variables here. Examples:
# var a = 2
# var b = "text"
var sound_effects_dict: Dictionary
#class_name FrameSoundEffects
#extends Resource
#
#
#export (String) var animation_name
#export(int) var frame_number
#export (AudioStreamSample) var sound
# Called when the node enters the scene tree for the first time.
func _ready():
# Trying something new with a custom resourse.
for i in sound_effects:
sound_effects_dict[i.animation_name + str(i.frame_number)] = i.sound
print (sound_effects_dict)
request_state_change = funcref(get_node(callable_state_machine), 'change_to_known_state')
## Connect signal to get alerted of state change
get_node(callable_state_machine).connect("state_changed", self,"_on_state_change")
## A reference to the current state machine state
current_state = get_node(callable_state_machine).current_state
# Experimenting with sound based resources I did this and it worked
#sound_effect_player.stream = sound_effects.sounds["pew"]
#print(sounds.sounds["pew"])
#sound_effects.play()
var last_sound_frame_animation: String = ''
var last_sound_frame: int = -1
func play_sound_frame(animation: String, frame: int ):
##DEBUG:
#if animation == 'run' and frame == 6:
# print("Do the thign! (", animation + str(frame), ")", " (", last_sound_frame_animation + str(last_sound_frame), ")")
if animation != last_sound_frame_animation or frame != last_sound_frame:
last_sound_frame = frame
last_sound_frame_animation = animation
var sound_index = animation + str(frame)
if sound_effects_dict.has(sound_index):
stream = sound_effects_dict[sound_index]
play()
print(self.name, " Playing SE: ", sound_index)
# Called every frame. 'delta' is the elapsed time since the previous frame.
#func _process(delta):
# pass

View File

@ -0,0 +1,7 @@
class_name SE_StateFrame
extends Resource
export (String) var state_name
export(int) var frame_number
export (AudioStreamSample) var sound

View File

@ -24,8 +24,10 @@ var gravity: int = ProjectSettings.get_setting("physics/2d/default_gravity")
#var adjusted_move_speed: float #var adjusted_move_speed: float
var jerk: float var jerk: float
## Variables intended to allow state receivers to communicate
var animation_finished: bool = false var animation_finished: bool = false
var animation_frame :int = -1
var movement_stopped: bool = false
# Not sure if this should be here. probably not # Not sure if this should be here. probably not
export(Array, String) var animation_sequence export(Array, String) var animation_sequence
@ -35,6 +37,8 @@ func enter() -> void:
# Call parent class enter # Call parent class enter
.enter() .enter()
animation_finished = false animation_finished = false
movement_stopped = false
animation_frame = -1
jerk = 0 jerk = 0
return return

View File

@ -4,9 +4,10 @@ extends Node
# Declare member variables here. Examples: # Declare member variables here. Examples:
# var a = 2 # var a = 2
# var b = "text" # var b = "text"
var player_start_position: Position2D ##TODO: Should be based on screen position for starter
onready var player_start_position := Vector2(50,50)
func change_level(_level_name :String): func change_level(_level_name :String, _position_name :String):
print("res://src/levels/" + _level_name + ".tscn" ) print("res://src/levels/" + _level_name + ".tscn" )
var SceneTransition = get_node("/root/Main/SceneTransition") var SceneTransition = get_node("/root/Main/SceneTransition")
#var simultaneous_scene = preload("res://levels/level2.tscn").instance() #var simultaneous_scene = preload("res://levels/level2.tscn").instance()
@ -21,6 +22,9 @@ func change_level(_level_name :String):
get_node("/root/Main").remove_child(l) get_node("/root/Main").remove_child(l)
get_node("/root/Main").add_child(new_level) get_node("/root/Main").add_child(new_level)
get_node("/root/Main").move_child(new_level,1) get_node("/root/Main").move_child(new_level,1)
##TODO: Probably set start position
if new_level.entrances.has(_position_name):
player_start_position = new_level.entrances[_position_name].transform.origin
print (get_node("/root/Main").get_children()) print (get_node("/root/Main").get_children())
SceneTransition.reset() SceneTransition.reset()
#get_node("/root/Main").add_child_below_node(SceneTransition,new_level) #get_node("/root/Main").add_child_below_node(SceneTransition,new_level)

View File

@ -1,7 +1,8 @@
[gd_scene load_steps=5 format=2] [gd_scene load_steps=6 format=2]
[ext_resource path="res://lib/classes/animated_sprite_state_receiver.gd" type="Script" id=1] [ext_resource path="res://lib/classes/animated_sprite_state_receiver.gd" type="Script" id=1]
[ext_resource path="res://lib/classes/state_machine.gd" type="Script" id=2] [ext_resource path="res://lib/classes/state_machine.gd" type="Script" id=2]
[ext_resource path="res://lib/classes/audiostreamplayer_state_receiver.gd" type="Script" id=3]
[ext_resource path="res://lib/classes/movement_state_receiver.gd" type="Script" id=5] [ext_resource path="res://lib/classes/movement_state_receiver.gd" type="Script" id=5]
[ext_resource path="res://lib/classes/actor.gd" type="Script" id=8] [ext_resource path="res://lib/classes/actor.gd" type="Script" id=8]
@ -33,4 +34,7 @@ callable_state_machine = NodePath("../Movement_StateMachine")
script = ExtResource( 5 ) script = ExtResource( 5 )
callable_state_machine = NodePath("../Movement_StateMachine") callable_state_machine = NodePath("../Movement_StateMachine")
[node name="SE_Player" type="AudioStreamPlayer" parent="."] [node name="AudioStreamPlayer_StateReceiver" type="AudioStreamPlayer" parent="."]
script = ExtResource( 3 )
callable_state_machine = NodePath("../Movement_StateMachine")
sound_effects = [ null ]

View File

@ -19,15 +19,10 @@ _global_script_classes=[ {
"language": "GDScript", "language": "GDScript",
"path": "res://lib/classes/animated_sprite_state_receiver.gd" "path": "res://lib/classes/animated_sprite_state_receiver.gd"
}, { }, {
"base": "Reference", "base": "AudioStreamPlayer",
"class": "DEPR_ModifierProperties", "class": "AudioStreamPlayer_StateReceiver",
"language": "GDScript", "language": "GDScript",
"path": "res://lib/classes/DEPR_state_modifier_properties.gd" "path": "res://lib/classes/audiostreamplayer_state_receiver.gd"
}, {
"base": "Reference",
"class": "DumbOldStateModifier",
"language": "GDScript",
"path": "res://lib/classes/DEPR_state_modifier.gd"
}, { }, {
"base": "", "base": "",
"class": "GitAPI", "class": "GitAPI",
@ -80,6 +75,11 @@ _global_script_classes=[ {
"path": "res://lib/classes/movement_state_receiver.gd" "path": "res://lib/classes/movement_state_receiver.gd"
}, { }, {
"base": "Resource", "base": "Resource",
"class": "SE_StateFrame",
"language": "GDScript",
"path": "res://lib/classes/sound_effect_state_frame.gd"
}, {
"base": "Resource",
"class": "State", "class": "State",
"language": "GDScript", "language": "GDScript",
"path": "res://lib/classes/state.gd" "path": "res://lib/classes/state.gd"
@ -117,8 +117,7 @@ _global_script_classes=[ {
_global_script_class_icons={ _global_script_class_icons={
"Actor": "", "Actor": "",
"AnimatedSprite_StateReceiver": "", "AnimatedSprite_StateReceiver": "",
"DEPR_ModifierProperties": "", "AudioStreamPlayer_StateReceiver": "",
"DumbOldStateModifier": "",
"GitAPI": "", "GitAPI": "",
"HealthComponent": "", "HealthComponent": "",
"HealthPickup": "", "HealthPickup": "",
@ -129,6 +128,7 @@ _global_script_class_icons={
"Modifier_Receiver": "", "Modifier_Receiver": "",
"MovementComponent": "", "MovementComponent": "",
"Movement_StateReceiver": "", "Movement_StateReceiver": "",
"SE_StateFrame": "",
"State": "", "State": "",
"StateAnimatedActor": "", "StateAnimatedActor": "",
"StateMachine": "", "StateMachine": "",

View File

@ -4,7 +4,8 @@ extends Interactable
## Things like 'door_right', 'stairs' ## Things like 'door_right', 'stairs'
## helps the Player object pick an appropriate animation ## helps the Player object pick an appropriate animation
export var _transition_type := 'door_right' export var _transition_type := 'door_right'
export var _destination_level_name: String
export var _destination_position_name := 'PlayerStart'
# Declare member variables here. Examples: # Declare member variables here. Examples:
# var a = 2 # var a = 2
# var b = "text" # var b = "text"
@ -15,4 +16,4 @@ func trigger_interaction():
# This is something that should maybe be extended for every differant interactible. # This is something that should maybe be extended for every differant interactible.
# They could inherit from this base class and implement this function. # They could inherit from this base class and implement this function.
print("Okay, I'll transition the level now!") print("Okay, I'll transition the level now!")
LevelInfo.change_level("CloneBox") LevelInfo.change_level(_destination_level_name, _destination_position_name)

View File

@ -54,6 +54,20 @@ func _on_state_change_fall():
change_animation(2) change_animation(2)
stop() stop()
var climb_latch:bool = false
func _state_process_climb():
UiManager.debug_text = str(frame)
if current_state.movement_stopped == true and climb_latch == false:
stop()
if frame != 0 and (frame + 1) >= frames.get_frame_count(animation):
frame = 0
else:
frame = frame + 1
climb_latch = true
if current_state.movement_stopped == false and climb_latch == true:
play()
climb_latch = false
#func _on_state_change_ledge_grab(): #func _on_state_change_ledge_grab():
# change_animation(1) # change_animation(1)
# stop() # stop()

View File

@ -77,7 +77,14 @@ func wants_roll() -> bool:
_wants_roll = false _wants_roll = false
return false return false
var _wants_climb :bool
func wants_climb() -> bool:
if Input.is_action_pressed("ui_up"):
_wants_climb = true
return true
else:
_wants_climb = false
return false
#TODO: This is probably not a good way to do this. #TODO: This is probably not a good way to do this.
# we want to check input once and make decisions based on # we want to check input once and make decisions based on
@ -102,6 +109,7 @@ func process_physics_input(delta):
wants_attack_secondary() wants_attack_secondary()
wants_dash() wants_dash()
wants_roll() wants_roll()
wants_climb()
func flip_sprite_to_movement_direction(): func flip_sprite_to_movement_direction():
if desired_movement_vector.x != 0.0: if desired_movement_vector.x != 0.0:
@ -130,6 +138,9 @@ func _state_process_physics_idle():
if _wants_attack_secondary == true: if _wants_attack_secondary == true:
request_state_change.call_func('attack_sword') request_state_change.call_func('attack_sword')
if $"../LadderDetector".is_colliding() and _wants_climb == true:
request_state_change.call_func('climb')
func _state_process_physics_attack_shoot(): func _state_process_physics_attack_shoot():
if current_state.animation_finished == true: if current_state.animation_finished == true:
request_state_change.call_func('idle') request_state_change.call_func('idle')
@ -169,8 +180,10 @@ func _state_process_physics_enter_right():
#flip_sprite_to_movement_direction() #flip_sprite_to_movement_direction()
if current_state.state_timeout.time_left == 0 and level_transition_latch == false: if current_state.state_timeout.time_left == 0 and level_transition_latch == false:
#desired_movement_vector.x = LEFT ##TODO: Optionally flip direction
parent.transform.x.x = LEFT #parent.transform.x.x = LEFT
## Reset global position.
parent.global_position = LevelInfo.player_start_position
current_state.state_timeout.start() current_state.state_timeout.start()
level_transition_latch = true level_transition_latch = true
elif current_state.state_timeout.time_left == 0 and level_transition_latch == true: elif current_state.state_timeout.time_left == 0 and level_transition_latch == true:
@ -251,6 +264,47 @@ func _state_process_physics_move():
move_actor_as_desired() move_actor_as_desired()
func get_climb_shape_location() -> Vector2:
if $"../LadderDetector".is_colliding():
var point: Vector2 = $"../LadderDetector".get_collision_point()
var shape_id = $"../LadderDetector".get_collider_shape()
var object = $"../LadderDetector".get_collider()
# This appears to get the shapes location!
var area = Physics2DServer.area_get_transform(object)
var areashape = Physics2DServer.area_get_shape_transform(object, shape_id)
var y_dir = Input.get_axis("ui_up" , "ui_down")
var global_origin = areashape.origin + area.origin
return Vector2(global_origin.x, y_dir)
else:
return Vector2(-1,-1)
func _state_process_physics_climb():
#$"../LadderDetector".set_enabled(false)
var ladder_location = get_climb_shape_location()
if ladder_location != Vector2(-1,-1):
#UiManager.debug_text = str(ladder_location) + '\n' + str(ladder_location - parent.global_position) #+ '\n' + str(parent.global_position.distance_to(ladder_location))
# An attempt to snap to the ladder location
if parent.global_position.x != round(ladder_location.x):
parent.global_translate(Vector2(round((ladder_location.x - parent.global_position.x)),(ladder_location.y * current_state.horizontal_speed) * physics_delta))
if ladder_location.y != 0:
#print("singal that I'm climbing?")
current_state.movement_stopped = false
else:
#print("singal that I'm not climbing?")
current_state.movement_stopped = true
# Make sure we hopped the step index
# if animation_index > 0:
# animations.stop()
else:
return request_state_change.call_func('idle')
if _wants_crouch:
request_state_change.call_func('fall')
func _state_process_physics_ledge_grab(): func _state_process_physics_ledge_grab():
UiManager.debug_text = (str(velocity)) UiManager.debug_text = (str(velocity))
$"../LedgeDetector".set_enabled(false) $"../LedgeDetector".set_enabled(false)
@ -274,10 +328,10 @@ func _state_process_physics_ledge_climb():
if parent.is_on_wall() == true: if parent.is_on_wall() == true:
#velocity = parent.move_and_slide(Vector2(10.0,-60.0),Vector2.UP) #velocity = parent.move_and_slide(Vector2(10.0,-60.0),Vector2.UP)
parent.move_and_slide(Vector2(10.0,-100.0),Vector2.UP) parent.move_and_slide(Vector2(sign(parent.transform.x.x) * 10.0,-100.0),Vector2.UP)
else: #parent.is_on_floor() == true: else: #parent.is_on_floor() == true:
#velocity = parent.move_and_slide(Vector2(10.0,10.0),Vector2.UP) #velocity = parent.move_and_slide(Vector2(10.0,10.0),Vector2.UP)
parent.move_and_slide(Vector2(60.0,10.0),Vector2.UP) parent.move_and_slide(Vector2(sign(parent.transform.x.x) * 60.0,10.0),Vector2.UP)
#velocity = parent.move_and_slide(Vector2(60.0,-60.0),Vector2.UP) #velocity = parent.move_and_slide(Vector2(60.0,-60.0),Vector2.UP)
# if parent.is_on_wall() != true: # if parent.is_on_wall() != true:

View File

@ -1,5 +1,6 @@
extends Actor extends Actor
export var player_number: int = 1
# Declare member variables here. Examples: # Declare member variables here. Examples:
# var a = 2 # var a = 2
@ -9,6 +10,8 @@ extends Actor
# Called when the node enters the scene tree for the first time. # Called when the node enters the scene tree for the first time.
func _ready(): func _ready():
PlayerInfo.player_health = $Health_Component.health PlayerInfo.player_health = $Health_Component.health
# Set initial player position in world.
global_position = LevelInfo.player_start_position
# Called every frame. 'delta' is the elapsed time since the previous frame. # Called every frame. 'delta' is the elapsed time since the previous frame.
@ -32,7 +35,8 @@ func touch_the_thing(the_thing: Interactable) -> bool:
the_thing.trigger_interaction() the_thing.trigger_interaction()
return false return false
if the_thing is LevelTransition: if the_thing is LevelTransition:
if the_thing._transition_type == 'door_right': if movement_state_machine.current_state.name != 'enter_right':
movement_state_machine.change_to_known_state('enter_right') if the_thing._transition_type == 'door_right':
the_thing.trigger_interaction() movement_state_machine.change_to_known_state('enter_right')
the_thing.trigger_interaction()
return true return true

View File

@ -1,4 +1,4 @@
[gd_scene load_steps=26 format=2] [gd_scene load_steps=27 format=2]
[ext_resource path="res://lib/templates/Actor/ActorTemplate.tscn" type="PackedScene" id=1] [ext_resource path="res://lib/templates/Actor/ActorTemplate.tscn" type="PackedScene" id=1]
[ext_resource path="res://assets/actors/players/playerE/PlayerE_SpriteFrames.tres" type="SpriteFrames" id=2] [ext_resource path="res://assets/actors/players/playerE/PlayerE_SpriteFrames.tres" type="SpriteFrames" id=2]
@ -22,6 +22,7 @@
[ext_resource path="res://src/actors/players/playerE/states/ledge_climb.tres" type="Resource" id=20] [ext_resource path="res://src/actors/players/playerE/states/ledge_climb.tres" type="Resource" id=20]
[ext_resource path="res://lib/templates/Interactable/Interactable_Receiver.gd" type="Script" id=21] [ext_resource path="res://lib/templates/Interactable/Interactable_Receiver.gd" type="Script" id=21]
[ext_resource path="res://src/actors/players/playerE/states/enter_right.tres" type="Resource" id=22] [ext_resource path="res://src/actors/players/playerE/states/enter_right.tres" type="Resource" id=22]
[ext_resource path="res://src/actors/players/playerE/states/climb.tres" type="Resource" id=23]
[sub_resource type="Resource" id=3] [sub_resource type="Resource" id=3]
resource_local_to_scene = true resource_local_to_scene = true
@ -46,10 +47,11 @@ extents = Vector2( 9, 15 )
[node name="PlayerE" instance=ExtResource( 1 )] [node name="PlayerE" instance=ExtResource( 1 )]
script = ExtResource( 3 ) script = ExtResource( 3 )
actor_type = "Player" actor_type = "Player"
player_number = 1
[node name="Movement_StateMachine" parent="." index="0"] [node name="Movement_StateMachine" parent="." index="0"]
starting_state_name = "idle" starting_state_name = "idle"
states = [ ExtResource( 4 ), ExtResource( 9 ), ExtResource( 7 ), ExtResource( 8 ), ExtResource( 12 ), ExtResource( 11 ), ExtResource( 10 ), ExtResource( 13 ), ExtResource( 14 ), ExtResource( 15 ), SubResource( 3 ), ExtResource( 19 ), ExtResource( 20 ), ExtResource( 22 ) ] states = [ ExtResource( 4 ), ExtResource( 9 ), ExtResource( 7 ), ExtResource( 8 ), ExtResource( 12 ), ExtResource( 11 ), ExtResource( 10 ), ExtResource( 13 ), ExtResource( 14 ), ExtResource( 15 ), SubResource( 3 ), ExtResource( 19 ), ExtResource( 20 ), ExtResource( 22 ), ExtResource( 23 ) ]
[node name="AnimatedSprite_StateReceiver" parent="." index="1"] [node name="AnimatedSprite_StateReceiver" parent="." index="1"]
frames = ExtResource( 2 ) frames = ExtResource( 2 )
@ -74,24 +76,32 @@ script = ExtResource( 6 )
[node name="LedgeDetector" type="RayCast2D" parent="." index="3"] [node name="LedgeDetector" type="RayCast2D" parent="." index="3"]
modulate = Color( 0, 1, 0, 1 ) modulate = Color( 0, 1, 0, 1 )
position = Vector2( 8, 5 ) position = Vector2( 8, -10 )
enabled = true enabled = true
cast_to = Vector2( 1.36422e-12, 1 ) cast_to = Vector2( 1.36422e-12, -1 )
[node name="WallDetector" type="RayCast2D" parent="." index="4"] [node name="WallDetector" type="RayCast2D" parent="." index="4"]
modulate = Color( 0, 1, 0, 1 ) modulate = Color( 0, 1, 0, 1 )
position = Vector2( 6, 10 ) position = Vector2( 6, -16 )
enabled = true enabled = true
cast_to = Vector2( 4, -4 ) cast_to = Vector2( 4, 4 )
[node name="CollisionShape2D" type="CollisionShape2D" parent="." index="6"] [node name="LadderDetector" type="RayCast2D" parent="." index="5"]
modulate = Color( 0, 1, 0, 1 )
enabled = true
cast_to = Vector2( 1.36422e-12, 20 )
collision_mask = 1024
collide_with_areas = true
collide_with_bodies = false
[node name="CollisionShape2D" type="CollisionShape2D" parent="." index="7"]
position = Vector2( 0, 2 ) position = Vector2( 0, 2 )
shape = SubResource( 1 ) shape = SubResource( 1 )
[node name="Health_Component" parent="." index="7" instance=ExtResource( 17 )] [node name="Health_Component" parent="." index="8" instance=ExtResource( 17 )]
max_health = 100 max_health = 100
[node name="Hurtbox_Component" parent="." index="8" instance=ExtResource( 16 )] [node name="Hurtbox_Component" parent="." index="9" instance=ExtResource( 16 )]
collision_layer = 16 collision_layer = 16
collision_mask = 128 collision_mask = 128
hurtbox_entered_function = "hit_Receiver" hurtbox_entered_function = "hit_Receiver"
@ -101,6 +111,6 @@ modulate = Color( 0, 0, 1, 1 )
position = Vector2( -1, 2 ) position = Vector2( -1, 2 )
shape = SubResource( 2 ) shape = SubResource( 2 )
[node name="Interactable_Receiver" type="Node" parent="." index="9"] [node name="Interactable_Receiver" type="Node" parent="." index="10"]
script = ExtResource( 21 ) script = ExtResource( 21 )
interactable_parent_callback = "touch_the_thing" interactable_parent_callback = "touch_the_thing"

View File

@ -0,0 +1,16 @@
[gd_resource type="Resource" load_steps=2 format=2]
[ext_resource path="res://lib/classes/state_animated_actor.gd" type="Script" id=1]
[resource]
resource_local_to_scene = true
script = ExtResource( 1 )
debug_state = false
timeout_seconds = 0.0
name = "climb"
horizontal_speed = 20.0
horizontal_acceleration = 0.0
horizontal_speed_offset = 0.0
horizontal_speed_offset_acceleration = 0.0
jerk_factor = 0.0
animation_sequence = [ "climb" ]

View File

@ -6,7 +6,7 @@
resource_local_to_scene = true resource_local_to_scene = true
script = ExtResource( 1 ) script = ExtResource( 1 )
debug_state = false debug_state = false
timeout_seconds = 1.5 timeout_seconds = 1.0
name = "enter_right" name = "enter_right"
horizontal_speed = 30.0 horizontal_speed = 30.0
horizontal_acceleration = 0.0 horizontal_acceleration = 0.0

View File

@ -7,12 +7,15 @@ extends Node2D
# var b = "text" # var b = "text"
onready var player_start = $PlayerStart onready var player_start = $PlayerStart
var entrances:Dictionary
# Called when the node enters the scene tree for the first time. # Called when the node enters the scene tree for the first time.
func _ready(): func _ready():
LevelInfo.player_start_position = player_start LevelInfo.player_start_position = player_start.transform.origin
for ent in get_children():
if ent is Position2D:
entrances[ent.name] = ent
# Called every frame. 'delta' is the elapsed time since the previous frame. # Called every frame. 'delta' is the elapsed time since the previous frame.
#func _process(delta): #func _process(delta):

View File

@ -11,7 +11,7 @@ radius = 5.09902
[node name="TileMap Collision" parent="." index="1"] [node name="TileMap Collision" parent="." index="1"]
tile_set = ExtResource( 2 ) tile_set = ExtResource( 2 )
tile_data = PoolIntArray( 0, 4, 65536, 19, 4, 65536, 65536, 4, 65536, 65555, 4, 65536, 131072, 4, 65536, 131091, 4, 65536, 196608, 4, 65536, 196620, 2, 0, 196621, 2, 1, 196622, 2, 2, 196627, 4, 65536, 262144, 4, 0, 262156, 2, 65536, 262157, 2, 65537, 262158, 2, 65538, 262163, 4, 0, 327680, 4, 65536, 327699, 4, 65536, 393216, 4, 65536, 458752, 4, 65536, 589823, 0, 1, 524288, 4, 131072, 524289, 0, 3, 524290, 0, 1, 524291, 0, 2, 524292, 0, 3, 524293, 0, 1, 524294, 0, 2, 524295, 0, 3, 524296, 0, 1, 524297, 0, 2, 524298, 0, 3, 524299, 0, 1, 524300, 0, 2, 524301, 0, 3, 524302, 0, 1, 524303, 0, 2, 524304, 0, 3, 524305, 0, 1, 524306, 0, 2, 524308, 0, 1, 524309, 0, 2, 524310, 0, 3, 655359, 0, 65537, 589824, 0, 65538, 589825, 0, 65539, 589826, 0, 65537, 589827, 0, 65538, 589828, 0, 65539, 589829, 0, 65537, 589830, 0, 65538, 589831, 0, 65539, 589832, 0, 65537, 589833, 0, 65538, 589834, 0, 65539, 589835, 0, 65537, 589836, 0, 65538, 589837, 0, 65539, 589838, 0, 65537, 589839, 0, 65538, 589840, 0, 65539, 589841, 0, 65537, 589842, 0, 65538, 589843, 0, 65539, 589844, 0, 65537, 589845, 0, 65538, 589846, 0, 65539, 720895, 0, 131073, 655360, 0, 131074, 655361, 0, 131075, 655362, 0, 131073, 655363, 0, 131074, 655364, 0, 131075, 655365, 0, 131073, 655366, 0, 131074, 655367, 0, 131075, 655368, 0, 131073, 655369, 0, 131074, 655370, 0, 131075, 655371, 0, 131073, 655372, 0, 131074, 655373, 0, 131075, 655374, 0, 131073, 655375, 0, 131074, 655376, 0, 131075, 655377, 0, 131073, 655378, 0, 131074, 655379, 0, 131075, 655380, 0, 131073, 655381, 0, 131074, 655382, 0, 131075, 786431, 0, 196609, 720896, 0, 196610, 720897, 0, 196611, 720898, 0, 196609, 720899, 0, 196610, 720900, 0, 196611, 720901, 0, 196609, 720902, 0, 196610, 720903, 0, 196611, 720904, 0, 196609, 720905, 0, 196610, 720906, 0, 196611, 720907, 0, 196609, 720908, 0, 196610, 720909, 0, 196611, 720910, 0, 196609, 720911, 0, 196610, 720912, 0, 196611, 720913, 0, 196609, 720914, 0, 196610, 720915, 0, 196611, 720916, 0, 196609, 720917, 0, 196610, 720918, 0, 196611, 851967, 0, 262145, 786432, 0, 262146, 786433, 0, 262147, 786434, 0, 262145, 786435, 0, 262146, 786436, 0, 262147, 786437, 0, 262145, 786438, 0, 262146, 786439, 0, 262147, 786440, 0, 262145, 786441, 0, 262146, 786442, 0, 262147, 786443, 0, 262145, 786444, 0, 262146, 786445, 0, 262147, 786446, 0, 262145, 786447, 0, 262146, 786448, 0, 262147, 786449, 0, 262145, 786450, 0, 262146, 786451, 0, 262147, 786452, 0, 262145, 786453, 0, 262146, 786454, 0, 262147 ) tile_data = PoolIntArray( -196609, 4, 0, -131073, 4, 0, -65537, 4, 0, -3, 4, 0, -2, 4, 0, -1, 4, 0, -65517, 4, 0, 65533, 4, 0, 19, 4, 65536, 131069, 4, 0, 65555, 4, 65536, 196605, 4, 0, 131073, 2, 1, 131074, 2, 2, 131091, 4, 65536, 262141, 4, 0, 262142, 4, 0, 262143, 4, 0, 196608, 4, 65536, 196609, 2, 65537, 196610, 2, 65538, 196627, 4, 65536, 262144, 4, 0, 262163, 4, 0, 327680, 4, 65536, 327699, 4, 65536, 393216, 4, 65536, 393235, 4, 65536, 458752, 4, 65536, 458771, 4, 65536, 589823, 0, 1, 524288, 4, 131072, 524289, 0, 3, 524290, 0, 1, 524291, 0, 2, 524292, 0, 3, 524293, 0, 1, 524294, 0, 2, 524295, 0, 3, 524296, 0, 1, 524297, 0, 2, 524298, 0, 3, 524299, 0, 1, 524300, 0, 2, 524301, 0, 3, 524302, 0, 1, 524303, 0, 2, 524304, 0, 3, 524305, 0, 1, 524306, 0, 2, 524307, 4, 0, 524308, 0, 1, 524309, 0, 2, 524310, 0, 3, 655359, 0, 65537, 589824, 0, 65538, 589825, 0, 65539, 589826, 0, 65537, 589827, 0, 65538, 589828, 0, 65539, 589829, 0, 65537, 589830, 0, 65538, 589831, 0, 65539, 589832, 0, 65537, 589833, 0, 65538, 589834, 0, 65539, 589835, 0, 65537, 589836, 0, 65538, 589837, 0, 65539, 589838, 0, 65537, 589839, 0, 65538, 589840, 0, 65539, 589841, 0, 65537, 589842, 0, 65538, 589843, 0, 65539, 589844, 0, 65537, 589845, 0, 65538, 589846, 0, 65539, 720895, 0, 131073, 655360, 0, 131074, 655361, 0, 131075, 655362, 0, 131073, 655363, 0, 131074, 655364, 0, 131075, 655365, 0, 131073, 655366, 0, 131074, 655367, 0, 131075, 655368, 0, 131073, 655369, 0, 131074, 655370, 0, 131075, 655371, 0, 131073, 655372, 0, 131074, 655373, 0, 131075, 655374, 0, 131073, 655375, 0, 131074, 655376, 0, 131075, 655377, 0, 131073, 655378, 0, 131074, 655379, 0, 131075, 655380, 0, 131073, 655381, 0, 131074, 655382, 0, 131075, 786431, 0, 196609, 720896, 0, 196610, 720897, 0, 196611, 720898, 0, 196609, 720899, 0, 196610, 720900, 0, 196611, 720901, 0, 196609, 720902, 0, 196610, 720903, 0, 196611, 720904, 0, 196609, 720905, 0, 196610, 720906, 0, 196611, 720907, 0, 196609, 720908, 0, 196610, 720909, 0, 196611, 720910, 0, 196609, 720911, 0, 196610, 720912, 0, 196611, 720913, 0, 196609, 720914, 0, 196610, 720915, 0, 196611, 720916, 0, 196609, 720917, 0, 196610, 720918, 0, 196611, 851967, 0, 262145, 786432, 0, 262146, 786433, 0, 262147, 786434, 0, 262145, 786435, 0, 262146, 786436, 0, 262147, 786437, 0, 262145, 786438, 0, 262146, 786439, 0, 262147, 786440, 0, 262145, 786441, 0, 262146, 786442, 0, 262147, 786443, 0, 262145, 786444, 0, 262146, 786445, 0, 262147, 786446, 0, 262145, 786447, 0, 262146, 786448, 0, 262147, 786449, 0, 262145, 786450, 0, 262146, 786451, 0, 262147, 786452, 0, 262145, 786453, 0, 262146, 786454, 0, 262147 )
[node name="TileMap Foreground" parent="." index="2"] [node name="TileMap Foreground" parent="." index="2"]
tile_set = ExtResource( 2 ) tile_set = ExtResource( 2 )
@ -19,6 +19,9 @@ collision_layer = 0
collision_mask = 0 collision_mask = 0
tile_data = PoolIntArray( 524288, 0, 2, 524307, 0, 3 ) tile_data = PoolIntArray( 524288, 0, 2, 524307, 0, 3 )
[node name="PlayerStart" parent="." index="3"]
position = Vector2( 147, 18 )
[node name="Hitbox_Component" parent="." index="4" instance=ExtResource( 3 )] [node name="Hitbox_Component" parent="." index="4" instance=ExtResource( 3 )]
damage_amount = 10 damage_amount = 10
@ -33,3 +36,6 @@ color = Color( 1, 0, 0, 1 )
modulate = Color( 1, 0, 0, 1 ) modulate = Color( 1, 0, 0, 1 )
position = Vector2( 213, 45 ) position = Vector2( 213, 45 )
shape = SubResource( 1 ) shape = SubResource( 1 )
[node name="EnterLeft" type="Position2D" parent="." index="5"]
position = Vector2( -13, 28 )

View File

@ -1,4 +1,4 @@
[gd_scene load_steps=7 format=2] [gd_scene load_steps=8 format=2]
[ext_resource path="res://src/templates/level_templates/LevelTemplate.tscn" type="PackedScene" id=1] [ext_resource path="res://src/templates/level_templates/LevelTemplate.tscn" type="PackedScene" id=1]
[ext_resource path="res://assets/levels/LegacyFantasy-High_Forest/tileset.tres" type="TileSet" id=2] [ext_resource path="res://assets/levels/LegacyFantasy-High_Forest/tileset.tres" type="TileSet" id=2]
@ -11,6 +11,9 @@ radius = 5.09902
[sub_resource type="RectangleShape2D" id=2] [sub_resource type="RectangleShape2D" id=2]
extents = Vector2( 4.5, 10 ) extents = Vector2( 4.5, 10 )
[sub_resource type="RectangleShape2D" id=3]
extents = Vector2( 8, 40 )
[node name="TestBox" instance=ExtResource( 1 )] [node name="TestBox" instance=ExtResource( 1 )]
[node name="TileMap Collision" parent="." index="1"] [node name="TileMap Collision" parent="." index="1"]
@ -23,6 +26,9 @@ collision_layer = 0
collision_mask = 0 collision_mask = 0
tile_data = PoolIntArray( 524288, 0, 2, 524307, 0, 3 ) tile_data = PoolIntArray( 524288, 0, 2, 524307, 0, 3 )
[node name="PlayerStart" parent="." index="3"]
position = Vector2( 80, 131 )
[node name="Hitbox_Component" parent="." index="4" instance=ExtResource( 3 )] [node name="Hitbox_Component" parent="." index="4" instance=ExtResource( 3 )]
damage_amount = 10 damage_amount = 10
@ -39,8 +45,30 @@ position = Vector2( 268, 119 )
shape = SubResource( 1 ) shape = SubResource( 1 )
[node name="LevelTransition" parent="." index="5" instance=ExtResource( 4 )] [node name="LevelTransition" parent="." index="5" instance=ExtResource( 4 )]
_destination_level_name = "CloneBox"
_destination_position_name = "EnterLeft"
[node name="CollisionShape2D" type="CollisionShape2D" parent="LevelTransition" index="0"] [node name="CollisionShape2D" type="CollisionShape2D" parent="LevelTransition" index="0"]
modulate = Color( 1, 0, 1, 1 ) modulate = Color( 1, 0, 1, 1 )
position = Vector2( 316, 121 ) position = Vector2( 316, 121 )
shape = SubResource( 2 ) shape = SubResource( 2 )
[node name="Ladder" type="Area2D" parent="." index="6"]
position = Vector2( 208, 64 )
collision_layer = 1024
collision_mask = 0
[node name="CollisionShape2D" type="CollisionShape2D" parent="Ladder" index="0"]
position = Vector2( 8, 40 )
shape = SubResource( 3 )
__meta__ = {
"_edit_lock_": true
}
[node name="ColorRect" type="ColorRect" parent="Ladder" index="1"]
margin_right = 16.0
margin_bottom = 80.0
color = Color( 0.45098, 0.192157, 0.192157, 1 )
__meta__ = {
"_edit_lock_": true
}

View File

@ -12,6 +12,7 @@ var animation_name = ''
func reset(): func reset():
$AnimationPlayer.play_backwards(animation_name) $AnimationPlayer.play_backwards(animation_name)
emit_signal("done")
func transition_dissolve(target: String) -> void: func transition_dissolve(target: String) -> void:
animation_name = 'dissolve' animation_name = 'dissolve'

View File

@ -96,5 +96,5 @@ anims/dissolve = SubResource( 4 )
[node name="clouds" type="TextureRect" parent="."] [node name="clouds" type="TextureRect" parent="."]
margin_top = 180.0 margin_top = 180.0
margin_right = 320.0 margin_right = 320.0
margin_bottom = 360.0 margin_bottom = 400.0
texture = ExtResource( 2 ) texture = ExtResource( 2 )