Merge branch 'main' into custom-level-loading-rewrite

This commit is contained in:
JHDev2006
2025-10-17 21:12:58 +01:00
200 changed files with 19511 additions and 16655 deletions

View File

@@ -14,6 +14,7 @@ func check_brick_empty() -> void:
func on_block_hit(player: Player) -> void:
if player.power_state.hitbox_size == "Big":
if item == null:
self.add_collision_exception_with(player) # Don't bonk with physics, will be handled after block is broken
await get_tree().physics_frame
destroy()
Global.score += 50

View File

@@ -8,18 +8,26 @@ extends Node
signal player_hit(player: Player)
signal player_stomped_on(player: Player)
signal invincible_player_hit(player: Player)
signal hammer_player_hit(player: Player)
func _ready() -> void:
hitbox.area_entered.connect(area_entered)
func area_entered(area: Area2D) -> void:
if area.owner is Player:
player_entered(area.owner)
if area.name == "HammerHitbox":
hammer_entered(area.owner)
else:
player_entered(area.owner)
func player_entered(player: Player) -> void:
if player.is_invincible or player.has_hammer:
if player.is_invincible:
invincible_player_hit.emit(player)
elif (player.velocity.y >= 15 or (player.global_position.y + height < owner.global_position.y)) and player.in_water == false:
player_stomped_on.emit(player)
else:
player_hit.emit(player)
func hammer_entered(player: Player) -> void:
if player.has_hammer:
hammer_player_hit.emit(player)

View File

@@ -10,7 +10,7 @@ extends Node
resource_json = value
update_resource()
enum ResourceMode {SPRITE_FRAMES, TEXTURE, AUDIO, RAW}
enum ResourceMode {SPRITE_FRAMES, TEXTURE, AUDIO, RAW, FONT}
@export var use_cache := true
static var cache := {}
@@ -113,10 +113,16 @@ func get_resource(json_file: JSON) -> Resource:
match mode:
ResourceMode.SPRITE_FRAMES:
var animation_json = {}
if json.has("animations"):
animation_json = json.get("animations")
elif source_json.has("animations"):
if source_json.has("animations"):
animation_json = source_json.get("animations")
elif json.has("animations"):
animation_json = json.get("animations")
if json.has("animation_overrides"):
for i in json.get("animation_overrides").keys():
animation_json[i] = json.get("animation_overrides")[i]
if animation_json != {}:
resource = load_image_from_path(source_resource_path)
if json.has("rect"):
@@ -156,6 +162,10 @@ func get_resource(json_file: JSON) -> Resource:
resource = load_audio_from_path(source_resource_path)
ResourceMode.RAW:
pass
ResourceMode.FONT:
resource = FontFile.new()
resource.load_bitmap_font(source_resource_path)
resource.set_meta("base_path", source_resource_path)
if cache.has(json_file.resource_path) == false and use_cache and not is_random:
cache[json_file.resource_path] = resource
return resource
@@ -180,11 +190,12 @@ func apply_properties(properties := {}) -> void:
obj.set(p, properties[i])
continue
func get_variation_json(json := {}) -> Dictionary:
var level_theme = Global.level_theme
if force_properties.has("Theme"):
level_theme = force_properties.Theme
for i in json.keys().filter(func(key): return key.contains("config:")):
get_config_file(current_resource_pack)
if config_to_use != {}:

View File

@@ -26,6 +26,8 @@ func _process(_delta: float) -> void:
get_parent().visible = percent < 1 and Settings.file.visuals.visible_timers
frame = lerp(0, 6, percent)
if percent >= warn_threshold and Settings.file.audio.extra_sfx == 1:
if node is Timer:
if node.is_stopped(): return
if can_warn:
can_warn = false
AudioManager.play_global_sfx("timer_warning")

View File

@@ -368,7 +368,7 @@ func close_save_menu() -> void:
current_state = EditorState.TILE_MENU
func handle_tile_cursor() -> void:
Input.set_custom_mouse_cursor(null)
var target_mouse_icon = null
var snapped_position = ((%TileCursor.get_global_mouse_position() - CURSOR_OFFSET).snapped(Vector2(16, 16))) + CURSOR_OFFSET
%TileCursor.global_position = (snapped_position)
var old_index := selected_tile_index
@@ -388,16 +388,16 @@ func handle_tile_cursor() -> void:
elif Input.is_action_pressed("editor_select") == false:
multi_selecting = false
place_tile(tile_position)
Input.set_custom_mouse_cursor(CURSOR_PENCIL)
target_mouse_icon = (CURSOR_PENCIL)
if Input.is_action_pressed("mb_right"):
if Input.is_action_pressed("editor_select") and not multi_selecting:
multi_select_start(tile_position)
Input.set_custom_mouse_cursor(CURSOR_RULER)
target_mouse_icon = (CURSOR_RULER)
elif Input.is_action_pressed("editor_select") == false:
multi_selecting = false
remove_tile(tile_position)
Input.set_custom_mouse_cursor(CURSOR_ERASOR)
target_mouse_icon = (CURSOR_ERASOR)
if current_state == EditorState.IDLE:
if Input.is_action_just_pressed("scroll_up"):
@@ -420,6 +420,8 @@ func handle_tile_cursor() -> void:
selected_tile_index = wrap(selected_tile_index, 0, tile_list.size())
on_tile_selected(tile_list[selected_tile_index])
show_scroll_preview()
Input.set_custom_mouse_cursor(target_mouse_icon)
func pick_tile(tile_position := Vector2i.ZERO) -> void:
if tile_layer_nodes[current_layer].get_used_cells().has(tile_position):

View File

@@ -14,6 +14,10 @@ func die() -> void:
func die_from_object(_node: Node2D) -> void:
destroy()
func die_from_hammer(_node: Node2D) -> void:
AudioManager.play_sfx("hammer_hit", global_position)
destroy()
func summon_particle() -> void:
var node = BARREL_DESTRUCTION_PARTICLE.instantiate()

View File

@@ -1,20 +1,14 @@
extends Node2D
extends Enemy
var target_player: Player = null
var velocity := Vector2.ZERO
const MOVE_SPEED := 30
const SMOKE_PARTICLE = preload("uid://d08nv4qtfouv1")
var direction := -1
signal killed
func _physics_process(delta: float) -> void:
target_player = get_tree().get_first_node_in_group("Players")
if $TrackJoint.is_attached == false:
handle_movement(delta)
$Sprite.scale.x = direction
$Sprite.scale.x = -direction
func handle_movement(delta: float) -> void:
var target_direction = sign(target_player.global_position.x - global_position.x)
@@ -30,22 +24,6 @@ func handle_movement(delta: float) -> void:
velocity = lerp(velocity, Vector2.ZERO, delta * 5)
global_position += velocity * delta
func on_area_entered(area: Area2D) -> void:
if area.owner is Player:
if area.owner.is_invincible:
die()
else:
area.owner.damage()
func die() -> void:
summon_smoke_particle()
queue_free()
killed.emit()
func flag_die() -> void:
die()
func summon_smoke_particle() -> void:
var particle = SMOKE_PARTICLE.instantiate()
particle.global_position = global_position

View File

@@ -1,7 +1,6 @@
extends Node2D
extends Enemy
@export_range(25, 180) var length := 80
@export_enum("Clockwise", "C-Clockwise") var direction := 0
@export_range(4, 12) var boo_amount := 10
@export var spread_boos := false
@@ -9,10 +8,3 @@ func _physics_process(delta: float) -> void:
%RotationJoint.global_rotation_degrees = wrap(%RotationJoint.global_rotation_degrees + (45 * [1, -1][direction]) * delta, 0, 360)
for i in $Boos.get_children():
i.get_node("Sprite").scale.x = sign(get_tree().get_first_node_in_group("Players").global_position.x + 1 - i.global_position.x)
func on_area_entered(area: Area2D) -> void:
if area.owner is Player:
area.owner.damage()
func flag_die() -> void:
queue_free()

View File

@@ -1,10 +1,9 @@
class_name BowserFlame
extends Node2D
extends Enemy
@export_enum("Straight", "Aimed") var mode := 0
var target_y := 0
var direction := -1
func _ready() -> void:
pass
@@ -16,14 +15,7 @@ func movement(delta: float) -> void:
if mode == 1:
global_position.y = move_toward(global_position.y, target_y, delta * 50)
global_position.x += (100 * direction) * delta
$Sprite.scale.x = direction
func flag_die() -> void:
queue_free()
func on_area_entered(area: Area2D) -> void:
if area.owner is Player:
area.owner.damage()
$Sprite.scale.x = -direction
func play_sfx() -> void:
AudioManager.play_sfx("bowser_flame", global_position)

View File

@@ -53,3 +53,8 @@ func flag_die() -> void:
func die() -> void:
killed.emit()
queue_free()
func die_from_hammer() -> void:
AudioManager.play_sfx("hammer_hit", global_position)
killed.emit()
queue_free()

View File

@@ -37,3 +37,12 @@ func flag_die() -> void:
Global.score += 500
if score_note_adder != null:
score_note_adder.spawn_note(500)
func die_from_hammer(obj: Node2D) -> void:
var dir = sign(global_position.x - obj.global_position.x)
if dir == 0:
dir = [-1, 1].pick_random()
DiscoLevel.combo_amount += 1
AudioManager.play_sfx("hammer_hit", global_position)
killed.emit(dir)
queue_free()

View File

@@ -1,7 +1,8 @@
extends PowerUpItem
func collect_item(_player: Player) -> void:
AudioManager.play_sfx("clock_get", global_position)
$Label/AnimationPlayer.play("Appear")
Global.time = clamp(Global.time + 100, 0, 999)
Global.score += 1000
func on_area_entered(area: Area2D) -> void:
if area.owner is Player:
AudioManager.play_sfx("clock_get", global_position)
$Label/AnimationPlayer.play("Appear")
Global.time = clamp(Global.time + 100, 0, 999)
Global.score += 1000

View File

@@ -24,8 +24,8 @@ func collect() -> void:
$Sprite.queue_free()
else:
queue_free()
if get_parent() is TileMapLayer:
get_parent().erase_cell(get_parent().local_to_map(position))
if get_parent() is TileMapLayer:
get_parent().erase_cell(get_parent().local_to_map(position))
func summon_block_coin() -> void:
var node = spinning_coin_scene.instantiate()

View File

@@ -1,4 +1,8 @@
extends PowerUpItem
func play_sfx() -> void:
AudioManager.play_sfx("hachisuke", global_position)
func on_area_entered(area: Area2D) -> void:
if area.owner is Player:
AudioManager.play_sfx("hachisuke", global_position)
Global.score += 8000
$ScoreNoteSpawner.spawn_note(8000)
queue_free()

View File

@@ -1,11 +1,8 @@
class_name Hammer
extends Node2D
var velocity := Vector2(0, -200)
var direction := -1
extends Enemy
func _ready() -> void:
velocity = Vector2(0, -200)
$Sprite.flip_h = direction == 1
$Animations.speed_scale = -direction
velocity.x = 120 * direction
@@ -16,10 +13,3 @@ func _physics_process(delta: float) -> void:
global_position += velocity * delta
velocity.y += (Global.entity_gravity / delta) * delta
velocity.y = clamp(velocity.y, -INF, Global.entity_max_fall_speed)
func flag_die() -> void:
queue_free()
func on_area_entered(area: Area2D) -> void:
if area.owner is Player:
area.owner.damage()

View File

@@ -1,8 +1,6 @@
extends PowerUpItem
func _physics_process(delta: float) -> void:
pass
func on_player_entered(player: Player) -> void:
player.hammer_get()
queue_free()
func on_area_entered(area: Area2D) -> void:
if area.owner is Player:
area.owner.hammer_get()
queue_free()

View File

@@ -6,11 +6,12 @@ const SMOKE_PARTICLE = preload("uid://d08nv4qtfouv1")
func _ready() -> void:
$AnimationPlayer.play("Float")
func collected() -> void:
total_collected += 1
AudioManager.play_sfx("key_collect", global_position)
summon_smoke_particle()
queue_free()
func on_area_entered(area: Area2D) -> void:
if area.owner is Player:
total_collected += 1
AudioManager.play_sfx("key_collect", global_position)
summon_smoke_particle()
queue_free()
func summon_smoke_particle() -> void:
var node = SMOKE_PARTICLE.instantiate()

View File

@@ -14,8 +14,9 @@ func _ready() -> void:
$Sprite.play("Collected")
set_visibility_layer_bit(0, false)
func on_player_entered(_player: Player) -> void:
collected()
func on_area_entered(area: Area2D) -> void:
if area.owner is Player:
collected()
func collected() -> void:
if already_collected:

View File

@@ -72,6 +72,6 @@ func on_player_entered(_player: Player) -> void:
func on_area_exited(area: Area2D) -> void:
if area.owner is Player:
if area.owner is Player and area.name != "HammerHitbox":
if area.owner.state_machine.state.name == "Climb":
area.owner.state_machine.transition_to("Normal")

View File

@@ -24,6 +24,7 @@ func explode() -> void:
func kick(object: Node2D) -> void:
AudioManager.play_sfx("kick", global_position)
object.kick_anim()
var kick_dir = sign(global_position.x - object.global_position.x)
velocity.x = 150 * kick_dir
direction = kick_dir

View File

@@ -10,9 +10,9 @@ func do_cycle() -> void:
AudioManager.play_sfx("burner", global_position)
do_animation()
await get_tree().create_timer(0.25, false).timeout
%Hitbox.set_deferred("disabled", false)
%Shape.set_deferred("disabled", false)
await get_tree().create_timer(1.5, false).timeout
%Hitbox.set_deferred("disabled", true)
%Shape.set_deferred("disabled", true)
$Timer.start()
func do_animation() -> void:

View File

@@ -1,18 +1,9 @@
class_name Explosion
extends Node2D
extends Enemy
const destructable_tiles := {Vector2i(4, 0): Rect2(32, 160, 16, 16), Vector2i(4, 2): Rect2(48, 160, 16, 16)}
const BLOCK_DESTRUCTION_PARTICLES = preload("uid://cyw7kk1em8h16")
func on_body_entered(body: Node2D) -> void:
if body is Block:
if body.destructable: body.destroy()
if body is Player:
body.damage()
func on_area_entered(area: Area2D) -> void:
if area.owner is Player:
area.owner.damage()

View File

@@ -43,7 +43,7 @@ func on_area_entered(area: Area2D) -> void:
if area.owner.has_node("ShellDetection"):
area.owner.die_from_object(self)
elif area.owner is Player:
if area.owner.is_invincible:
if area.owner.is_invincible or area.name == "HammerHitbox":
destroy()
else:
area.owner.damage()

View File

@@ -64,14 +64,17 @@ func update_visuals() -> void:
hide()
func exit_pipe() -> void:
can_enter = false
pipe_exited.emit()
await get_tree().physics_frame
for i in get_tree().get_nodes_in_group("Players"):
if i.is_node_ready() == false:
await i.ready
i.go_to_exit_pipe(self)
for i in get_tree().get_nodes_in_group("Players"):
await get_tree().create_timer(0.5, false).timeout
await i.exit_pipe(self)
exiting_pipe_id = -1
can_enter = true
func get_vector(direction := 0) -> Vector2:
match direction:

View File

@@ -52,6 +52,7 @@ var input_direction := 0
var flight_meter := 0.0
var velocity_direction := 1
var velocity_x_jump_stored := 0
var total_keys := 0
@@ -74,6 +75,9 @@ var can_bump_crouch = false
var can_bump_swim = false
var can_bump_fly = false
var kicking = false
var can_kick_anim = false
@export var player_id := 0
const ONE_UP_NOTE = preload("uid://dopxwjj37gu0l")
var gravity := FALL_GRAVITY
@@ -146,31 +150,39 @@ const ANIMATION_FALLBACKS := {
"Pipe": "Idle",
"Walk": "Move",
"Run": "Move",
"PipeWalk": "Move",
"PipeWalk": "Walk",
"LookUp": "Idle",
"WaterLookUp": "LookUp",
"WingLookUp": "WaterLookUp",
"Crouch": "Idle",
"WaterCrouch": "Crouch",
"WingCrouch": "WaterCrouch",
"CrouchFall": "Crouch",
"CrouchJump": "Crouch",
"CrouchBump": "Bump",
"CrouchMove": "Crouch",
"IdleAttack": "Attack",
"IdleAttack": "MoveAttack",
"CrouchAttack": "IdleAttack",
"MoveAttack": "IdleAttack",
"MoveAttack": "Attack",
"WalkAttack": "MoveAttack",
"RunAttack": "MoveAttack",
"SkidAttack": "MoveAttack",
"FlyIdle": "SwimIdle",
"WingIdle": "WaterIdle",
"FlyUp": "SwimUp",
"FlyMove": "SwimMove",
"WingMove": "WaterMove",
"FlyAttack": "SwimAttack",
"FlyBump": "SwimBump",
"FlagSlide": "Climb",
"WaterMove": "Move",
"WaterIdle": "Idle",
"FlyIdle": "SwimIdle",
"SwimBump": "Bump",
"DieFreeze": "Die",
"RunJump": "Jump",
"RunJumpFall": "JumpFall",
"RunJumpBump": "JumpBump",
"StarJump": "Jump",
"StarFall": "StarJump"
"StarFall": "JumpFall"
}
var palette_transform := true
@@ -270,6 +282,7 @@ func _physics_process(delta: float) -> void:
set_power_state_frame()
if Input.is_action_just_pressed("debug_noclip") and Global.debug_mode:
state_machine.transition_to("NoClip")
Global.log_comment("NOCLIP Enabled")
up_direction = -gravity_vector
handle_directions()
handle_block_collision_detection()
@@ -317,6 +330,7 @@ func _process(delta: float) -> void:
if is_invincible:
DiscoLevel.combo_meter = 100
%Hammer.visible = has_hammer
%HammerHitbox.collision_layer = has_hammer
func apply_gravity(delta: float) -> void:
if in_water or flight_meter > 0:
@@ -448,6 +462,11 @@ func bump_ceiling() -> void:
await get_tree().create_timer(0.1).timeout
bumping = false
func kick_anim() -> void:
kicking = true
await get_tree().create_timer(0.2).timeout
kicking = false
func super_star() -> void:
DiscoLevel.combo_meter += 1
is_invincible = true
@@ -670,6 +689,7 @@ func set_power_state_frame() -> void:
can_bump_crouch = %Sprite.sprite_frames.has_animation("CrouchBump")
can_bump_swim = %Sprite.sprite_frames.has_animation("SwimBump")
can_bump_fly = %Sprite.sprite_frames.has_animation("FlyBump")
can_kick_anim = %Sprite.sprite_frames.has_animation("Kick")
func get_power_up(power_name := "") -> void:
if is_dead:
@@ -796,7 +816,7 @@ func hide_pipe_animation() -> void:
func go_to_exit_pipe(pipe: PipeArea) -> void:
Global.can_time_tick = false
pipe_enter_direction = Vector2.ZERO
state_machine.transition_to("Pipe")
state_machine.transition_to("Freeze")
global_position = pipe.global_position + (pipe.get_vector(pipe.enter_direction) * 32)
if pipe.enter_direction == 1:
global_position = pipe.global_position + Vector2(0, -8)
@@ -821,6 +841,7 @@ func jump() -> void:
if spring_bouncing:
return
velocity.y = calculate_jump_height() * gravity_vector.y
velocity_x_jump_stored = velocity.x
gravity = JUMP_GRAVITY
AudioManager.play_sfx("small_jump" if power_state.hitbox_size == "Small" else "big_jump", global_position)
has_jumped = true
@@ -873,9 +894,6 @@ func hammer_get() -> void:
$HammerTimer.start()
AudioManager.set_music_override(AudioManager.MUSIC_OVERRIDES.HAMMER, 0, false)
func on_hammer_area_entered(area: Area2D) -> void:
pass
func wing_get() -> void:
AudioManager.set_music_override(AudioManager.MUSIC_OVERRIDES.WING, 0, false, false)
flight_meter = 10

View File

@@ -94,6 +94,7 @@ func kick(hit_player: Player) -> void:
DiscoLevel.combo_meter += 25
moving = true
moving_time = 0.0
hit_player.kick_anim()
if can_air_kick:
$ScoreNoteSpawner.spawn_note(8000)
else:

View File

@@ -2,8 +2,8 @@ extends PowerUpState
var fireball_amount := 0
const FIREBALL = preload("res://Scenes/Prefabs/Entities/Items/Fireball.tscn")
func update(_delta: float) -> void:
if Global.player_action_just_pressed("action", player.player_id) and fireball_amount < 2 and player.state_machine.state.name == "Normal":
func update(delta: float) -> void:
if Global.player_action_just_pressed("action", player.player_id) and fireball_amount < 2 and player.state_machine.state.name == "Normal" and delta > 0:
throw_fireball()
func throw_fireball() -> void:

View File

@@ -38,6 +38,7 @@ const DEFAULT_SFX_LIBRARY := {
"firework": "res://Assets/Audio/SFX/Firework.wav",
"timer_beep": "res://Assets/Audio/SFX/TimerBeep.wav",
"hachisuke": "res://Assets/Audio/SFX/Hachisuke.wav",
"hammer_hit": "res://Assets/Audio/SFX/HammerHit.wav",
"burner": "res://Assets/Audio/SFX/Burner.wav",
"rank_up_1": "res://Assets/Audio/SFX/RankUpCBA.wav",
"rank_up_2": "res://Assets/Audio/SFX/RankUpSP.wav",
@@ -88,7 +89,7 @@ const OVERRIDE_STREAMS := [
"res://Assets/Audio/BGM/CastleFinish.json",
"res://Assets/Audio/BGM/Ending.json",
"res://Assets/Audio/SFX/FlagSlide.wav",
"res://Assets/Audio/BGM/Hammer.mp3",
("res://Assets/Audio/BGM/Hammer.json"),
("res://Assets/Audio/BGM/LoseRace.json"),
("res://Assets/Audio/BGM/WinRace.json"),
"res://Assets/Audio/BGM/Wing.json",
@@ -100,6 +101,7 @@ const MUSIC_BASE = preload("uid://da4vqkrpqnma0")
var character_sfx_map := {}
var audio_override_queue := []
#var audio_override_queue: Array[Dictionary] = []
func play_sfx(stream_name = "", position := Vector2.ZERO, pitch := 1.0) -> void:
@@ -158,6 +160,8 @@ func kill_sfx(sfx_name := "") -> void:
func set_music_override(stream: MUSIC_OVERRIDES, priority := 0, stop_on_finish := true, restart := true) -> void:
if audio_override_queue.has(stream):
if current_music_override == stream and restart:
music_override_player.stream = create_stream_from_json(OVERRIDE_STREAMS[stream])
music_override_player.bus = "Music" if stream != MUSIC_OVERRIDES.FLAG_POLE else "SFX"
music_override_player.play()
return
if music_override_priority > priority:
@@ -175,7 +179,6 @@ func set_music_override(stream: MUSIC_OVERRIDES, priority := 0, stop_on_finish :
await music_override_player.finished
stop_music_override(stream)
func stop_music_override(stream: MUSIC_OVERRIDES, force := false) -> void:
if not force:
if stream == null:
@@ -183,16 +186,17 @@ func stop_music_override(stream: MUSIC_OVERRIDES, force := false) -> void:
elif stream != current_music_override:
audio_override_queue.erase(stream)
return
else:
audio_override_queue.clear()
audio_override_queue.pop_back()
current_music_override = MUSIC_OVERRIDES.NONE
music_override_player.stop()
music_override_priority = -1
if audio_override_queue.is_empty():
audio_override_queue.clear()
music_override_priority = -1
current_music_override = MUSIC_OVERRIDES.NONE
music_override_player.stop()
else:
current_music_override = audio_override_queue[audio_override_queue.size() - 1]
set_music_override(audio_override_queue[audio_override_queue.size() - 1])
func load_sfx_map(json := {}) -> void:
@@ -245,8 +249,9 @@ func handle_music_override() -> void:
music_override_player.get_stream_playback().switch_to_clip(0)
func create_stream_from_json(json_path := "") -> AudioStream:
var path := ""
if json_path.contains(".json") == false:
var path = ResourceSetter.get_pure_resource_path(json_path)
path = ResourceSetter.get_pure_resource_path(json_path)
if path.contains(Global.config_path):
match json_path.get_slice(".", 1):
"wav":
@@ -258,8 +263,7 @@ func create_stream_from_json(json_path := "") -> AudioStream:
elif path.contains("res://"):
return load(path)
var bgm_file = $ResourceSetterNew.get_variation_json(JSON.parse_string(FileAccess.open(ResourceSetter.get_pure_resource_path(json_path), FileAccess.READ).get_as_text()).variations).source
var path = json_path.replace(json_path.get_file(), bgm_file)
path = ResourceSetter.get_pure_resource_path(path)
path = ResourceSetter.get_pure_resource_path(json_path.replace(json_path.get_file(), bgm_file))
var stream = null
if path.get_file().contains(".bgm"):
stream = generate_interactive_stream(JSON.parse_string(FileAccess.open(path, FileAccess.READ).get_as_text()))

View File

@@ -34,7 +34,7 @@ var ROM_POINTER_PATH = config_path.path_join("rom_pointer.smb")
var ROM_PATH = config_path.path_join("baserom.nes")
var ROM_ASSETS_PATH = config_path.path_join("resource_packs/BaseAssets")
const ROM_PACK_NAME := "BaseAssets"
const ROM_ASSETS_VERSION := 0
const ROM_ASSETS_VERSION := 1
var server_version := -1
var current_version := -1
@@ -235,6 +235,7 @@ func check_for_rom() -> void:
if pack_dict.get("version", -1) == ROM_ASSETS_VERSION:
rom_assets_exist = true
else:
ResourceGenerator.updating = true
OS.move_to_trash(ROM_ASSETS_PATH)
func _process(delta: float) -> void:
@@ -245,6 +246,10 @@ func _process(delta: float) -> void:
AudioManager.current_level_theme = ""
level_theme_changed.emit()
log_comment("Reloaded resource packs!")
if Input.is_action_just_pressed("toggle_fps_count"):
%FPSCount.visible = !%FPSCount.visible
%FPSCount.text = str(int(Engine.get_frames_per_second())) + " FPS"
handle_p_switch(delta)
if Input.is_key_label_pressed(KEY_F11) and debug_mode == false and OS.is_debug_build():
@@ -259,6 +264,10 @@ func take_screenshot() -> void:
var img: Image = get_viewport().get_texture().get_image()
var filename = Global.config_path.path_join("screenshots/screenshot_" + str(int(Time.get_unix_time_from_system())) + ".png")
var err = img.save_png(filename)
if !err:
log_comment("Screenshot Saved!")
else:
log_error(error_string(err))
func handle_p_switch(delta: float) -> void:
if p_switch_active and get_tree().paused == false:
@@ -458,7 +467,7 @@ func check_completionist_achievement() -> void:
if achievements.count("0") == 1:
unlock_achievement(AchievementID.COMPLETIONIST)
const FONT = preload("uid://cd221873lbtj1")
const FONT = preload("res://Assets/Sprites/UI/Font.fnt")
func sanitize_string(string := "") -> String:
string = string.to_upper()
@@ -466,3 +475,11 @@ func sanitize_string(string := "") -> String:
if FONT.has_char(string.unicode_at(i)) == false and string[i] != "\n":
string = string.replace(string[i], " ")
return string
func get_base_asset_version() -> int:
var json = JSON.parse_string(FileAccess.open("user://BaseAssets/pack_info.json", FileAccess.READ).get_as_text())
var version = json.version
return get_version_num_int(version)
func get_version_num_int(ver_num := "0.0.0") -> int:
return int(ver_num.replace(".", ""))

View File

@@ -10,6 +10,7 @@ var file := {
"visuals": 0,
"hud_size": 0,
"frame_limit" : 0,
"window_size": [256, 240]
},
"audio": {
"master": 10,
@@ -94,6 +95,11 @@ func _enter_tree() -> void:
await get_tree().physics_frame
apply_settings()
TranslationServer.set_locale(Settings.file.game.lang)
get_window().size_changed.connect(update_window_size)
func update_window_size() -> void:
var window_size = get_window().size
Settings.file.video.window_size = [window_size.x, window_size.y]
func save_settings() -> void:
var cfg_file = ConfigFile.new()
@@ -112,6 +118,12 @@ func load_settings() -> void:
for section in cfg_file.get_sections():
for key in cfg_file.get_section_keys(section):
file[section][key] = cfg_file.get_value(section, key)
fix_broken_settings()
func fix_broken_settings() -> void:
# Fix any "permanently-enabled" resource packs from 1.0.2 snapshots after portable mode was added, but before this bug was fixed
for i in range(file.visuals.resource_packs.size()):
file.visuals.resource_packs[i] = str(file.visuals.resource_packs[i]).trim_prefix("/")
func apply_settings() -> void:
for i in file.video.keys():

View File

@@ -13,7 +13,7 @@ func enter(msg := {}) -> void:
player.set_collision_mask_value(i + 1, false)
player.gravity = player.JUMP_GRAVITY
if msg["Pit"] == false:
player.velocity.y = -player.DEATH_JUMP_HEIGHT
player.velocity.y = -player.DEATH_JUMP_HEIGHT * player.gravity_vector.y # nabbup : Flip death gravity when upside down
func physics_update(delta: float) -> void:
if can_fall:
@@ -22,8 +22,9 @@ func physics_update(delta: float) -> void:
player.play_animation("DieFreeze")
player.sprite.speed_scale = 1
if can_fall:
player.velocity.y += (player.JUMP_GRAVITY / delta) * delta
player.velocity.y = clamp(player.velocity.y, -INF, player.MAX_FALL_SPEED)
# nabbup : Flip death gravity when upside down
player.velocity.y += (player.JUMP_GRAVITY / delta) * delta * player.gravity_vector.y
player.velocity.y = clamp(player.velocity.y, -player.MAX_FALL_SPEED, player.MAX_FALL_SPEED) # wish this could be better than just substituting -INF but you can't win em all ~ nabbup
player.move_and_slide()
if Input.is_action_just_pressed("ui_accept") or Input.is_action_just_pressed("jump_0"):
player.death_load()

View File

@@ -15,6 +15,7 @@ func physics_update(_delta: float) -> void:
player.move_and_slide()
if Input.is_action_just_pressed("jump_0"):
state_machine.transition_to("Normal")
Global.log_comment("NOCLIP Disabled")
func exit() -> void:
player.can_hurt = false

View File

@@ -209,18 +209,25 @@ func get_animation_name() -> String:
return "FlyAttack"
else:
return "AirAttack"
if player.kicking and player.can_kick_anim:
return "Kick"
if player.crouching and not wall_pushing:
if player.bumping and player.can_bump_crouch:
return "CrouchBump"
elif player.is_on_floor() == false:
if player.velocity.y > 0:
if player.velocity.y >= 0:
return "CrouchFall"
elif player.velocity.y < 0:
return "CrouchJump"
elif player.is_actually_on_floor():
if abs(player.velocity.x) >= 5 and not player.is_actually_on_wall():
return "CrouchMove"
return "Crouch"
elif player.in_water:
return "WaterCrouch"
elif player.flight_meter > 0:
return "WingCrouch"
else:
return "Crouch"
if player.is_actually_on_floor():
if player.skidding:
return "Skid"
@@ -228,17 +235,26 @@ func get_animation_name() -> String:
if player.in_water:
return "WaterMove"
elif player.flight_meter > 0:
return "FlyMove"
return "WingMove"
elif abs(player.velocity.x) < player.RUN_SPEED - 10:
return "Walk"
else:
return "Run"
else:
if player.in_water or player.flight_meter > 0:
return "WaterIdle"
if Global.player_action_pressed("move_up", player.player_id):
return "LookUp"
return "Idle"
if player.in_water:
return "WaterLookUp"
elif player.flight_meter > 0:
return "WingLookUp"
else:
return "LookUp"
else:
if player.in_water:
return "WaterIdle"
elif player.flight_meter > 0:
return "WingIdle"
else:
return "Idle"
else:
if player.in_water:
if swim_up_meter > 0:
@@ -258,15 +274,24 @@ func get_animation_name() -> String:
return "FlyIdle"
if player.has_jumped:
if player.bumping and player.can_bump_jump:
return "JumpBump"
if abs(player.velocity_x_jump_stored) < player.RUN_SPEED - 10:
return "JumpBump"
else:
return "RunJumpBump"
elif player.velocity.y < 0:
if player.is_invincible:
return "StarJump"
return "Jump"
elif abs(player.velocity_x_jump_stored) < player.RUN_SPEED - 10:
return "Jump"
else:
return "RunJump"
else:
if player.is_invincible:
return "StarFall"
return "JumpFall"
elif abs(player.velocity_x_jump_stored) < player.RUN_SPEED - 10:
return "JumpFall"
else:
return "RunJumpFall"
else:
# guzlad: Fixes characters with fall anims not playing them, but also prevents old characters without that anim not being accurate
if !player.sprite.sprite_frames.has_animation("Fall"):
@@ -274,5 +299,6 @@ func get_animation_name() -> String:
return "Fall"
func exit() -> void:
player.on_hammer_timeout()
player.skidding = false
if owner.has_hammer:
owner.on_hammer_timeout()
owner.skidding = false